Merge branch 'master' of git@scm.dev.nokia.troll.no:creator/mainline

Conflicts:
	src/plugins/qmlinspector/qmlinspectorplugin.h
This commit is contained in:
Lasse Holmstedt
2010-02-16 16:55:47 +01:00
85 changed files with 2275 additions and 835 deletions

View File

@@ -56,9 +56,11 @@
#include <stdio.h>
#include <string.h>
QT_QML_BEGIN_NAMESPACE
QT_BEGIN_NAMESPACE
extern double qstrtod(const char *s00, char const **se, bool *ok);
QT_END_NAMESPACE
QT_QML_BEGIN_NAMESPACE
#define shiftWindowsLineBreak() \
do { \

View File

@@ -96,7 +96,8 @@ void FancyTabBar::paintEvent(QPaintEvent *event)
paintTab(&p, i);
// paint active tab last, since it overlaps the neighbors
paintTab(&p, currentIndex());
if (currentIndex() != -1)
paintTab(&p, currentIndex());
}
// Handle hover events for mouse fade ins
@@ -205,6 +206,7 @@ void FancyTabBar::paintTab(QPainter *painter, int tabIndex) const
bool selected = (tabIndex == m_currentIndex);
bool hover = (tabIndex == m_hoverIndex);
bool enabled = isTabEnabled(tabIndex);
#ifdef Q_WS_MAC
hover = false; // Do not hover on Mac
@@ -233,7 +235,7 @@ void FancyTabBar::paintTab(QPainter *painter, int tabIndex) const
painter->drawLine(rect.bottomLeft(), rect.bottomRight());
} else {
painter->fillRect(rect, background);
if (hover)
if (hover && enabled)
painter->fillRect(rect, hoverColor);
painter->setPen(QPen(light, 0));
painter->drawLine(rect.topLeft(), rect.topRight());
@@ -250,25 +252,55 @@ void FancyTabBar::paintTab(QPainter *painter, int tabIndex) const
painter->setFont(boldFont);
painter->setPen(selected ? Utils::StyleHelper::panelTextColor() : QColor(30, 30, 30, 80));
int textFlags = Qt::AlignCenter | Qt::AlignBottom | Qt::ElideRight | Qt::TextWordWrap;
painter->drawText(tabTextRect, textFlags, tabText);
painter->setPen(selected ? QColor(60, 60, 60) : Utils::StyleHelper::panelTextColor());
if (enabled) {
painter->drawText(tabTextRect, textFlags, tabText);
painter->setPen(selected ? QColor(60, 60, 60) : Utils::StyleHelper::panelTextColor());
} else {
painter->setPen(selected ? Utils::StyleHelper::panelTextColor() : QColor(255, 255, 255, 120));
}
int textHeight = painter->fontMetrics().boundingRect(QRect(0, 0, width(), height()), Qt::TextWordWrap, tabText).height();
tabIconRect.adjust(0, 4, 0, -textHeight);
int iconSize = qMin(tabIconRect.width(), tabIconRect.height());
if (iconSize > 4)
style()->drawItemPixmap(painter, tabIconRect, Qt::AlignCenter | Qt::AlignVCenter,
tabIcon(tabIndex).pixmap(tabIconRect.size()));
tabIcon(tabIndex).pixmap(tabIconRect.size(), enabled ? QIcon::Normal : QIcon::Disabled));
painter->translate(0, -1);
painter->drawText(tabTextRect, textFlags, tabText);
painter->restore();
}
void FancyTabBar::setCurrentIndex(int index) {
m_currentIndex = index;
update();
emit currentChanged(index);
if (isTabEnabled(index)) {
m_currentIndex = index;
update();
emit currentChanged(index);
}
}
void FancyTabBar::setTabEnabled(int index, bool enable)
{
Q_ASSERT(index < m_tabs.size());
Q_ASSERT(index >= 0);
if (index < m_tabs.size() && index >= 0) {
m_tabs[index].enabled = enable;
update(tabRect(index));
}
}
bool FancyTabBar::isTabEnabled(int index) const
{
Q_ASSERT(index < m_tabs.size());
Q_ASSERT(index >= 0);
if (index < m_tabs.size() && index >= 0)
return m_tabs[index].enabled;
return false;
}
//////
// FancyColorButton
//////
@@ -410,7 +442,8 @@ QStatusBar *FancyTabWidget::statusBar() const
void FancyTabWidget::setCurrentIndex(int index)
{
m_tabBar->setCurrentIndex(index);
if (m_tabBar->isTabEnabled(index))
m_tabBar->setCurrentIndex(index);
}
void FancyTabWidget::showWidget(int index)
@@ -424,3 +457,13 @@ void FancyTabWidget::setTabToolTip(int index, const QString &toolTip)
{
m_tabBar->setTabToolTip(index, toolTip);
}
void FancyTabWidget::setTabEnabled(int index, bool enable)
{
m_tabBar->setTabEnabled(index, enable);
}
bool FancyTabWidget::isTabEnabled(int index) const
{
return m_tabBar->isTabEnabled(index);
}

View File

@@ -48,6 +48,7 @@ namespace Internal {
QIcon icon;
QString text;
QString toolTip;
bool enabled;
};
class FancyTabBar : public QWidget
@@ -70,8 +71,12 @@ public:
QSize sizeHint() const;
QSize minimumSizeHint() const;
void setTabEnabled(int index, bool enable);
bool isTabEnabled(int index) const;
void insertTab(int index, const QIcon &icon, const QString &label) {
FancyTab tab;
tab.enabled = true;
tab.icon = icon;
tab.text = label;
m_tabs.insert(index, tab);
@@ -130,6 +135,9 @@ public:
int currentIndex() const;
QStatusBar *statusBar() const;
void setTabEnabled(int index, bool enable);
bool isTabEnabled(int index) const;
signals:
void currentAboutToShow(int index);
void currentChanged(int index);

View File

@@ -610,7 +610,7 @@ CPPEditor::CPPEditor(QWidget *parent)
, m_firstRenameChange(false)
{
m_initialized = false;
qRegisterMetaType<SemanticInfo>("SemanticInfo");
qRegisterMetaType<CppEditor::Internal::SemanticInfo>("CppEditor::Internal::SemanticInfo");
m_semanticHighlighter = new SemanticHighlighter(this);
m_semanticHighlighter->start();
@@ -700,8 +700,8 @@ void CPPEditor::createToolBar(CPPEditorEditable *editable)
connect(this, SIGNAL(cursorPositionChanged()), this, SLOT(updateUses()));
connect(this, SIGNAL(textChanged()), this, SLOT(updateUses()));
connect(m_semanticHighlighter, SIGNAL(changed(SemanticInfo)),
this, SLOT(updateSemanticInfo(SemanticInfo)));
connect(m_semanticHighlighter, SIGNAL(changed(CppEditor::Internal::SemanticInfo)),
this, SLOT(updateSemanticInfo(CppEditor::Internal::SemanticInfo)));
QToolBar *toolBar = static_cast<QToolBar*>(editable->toolBar());
QList<QAction*> actions = toolBar->actions();

View File

@@ -141,7 +141,7 @@ public:
void rehighlight(const Source &source);
Q_SIGNALS:
void changed(const SemanticInfo &semanticInfo);
void changed(const CppEditor::Internal::SemanticInfo &semanticInfo);
protected:
virtual void run();
@@ -242,7 +242,7 @@ private Q_SLOTS:
void onContentsChanged(int position, int charsRemoved, int charsAdded);
void semanticRehighlight();
void updateSemanticInfo(const SemanticInfo &semanticInfo);
void updateSemanticInfo(const CppEditor::Internal::SemanticInfo &semanticInfo);
void performQuickFix(int index);

View File

@@ -32,7 +32,9 @@
#include "formeditoritem.h"
QT_BEGIN_NAMESPACE
class QGraphicsItem;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -35,7 +35,9 @@
#include <qmlitemnode.h>
#include "snappinglinecreator.h"
QT_BEGIN_NAMESPACE
class QTimeLine;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -37,8 +37,9 @@
#include <qmlitemnode.h>
#include "abstractformeditortool.h"
QT_BEGIN_NAMESPACE
class QGraphicsSceneMouseEvent;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -498,7 +498,7 @@ QmlItemNode findRecursiveQmlItemNode(const QmlObjectNode &firstQmlObjectNode)
return QmlItemNode();
}
void FormEditorView::transformChanged(const QmlObjectNode &qmlObjectNode)
void FormEditorView::transformChanged(const QmlObjectNode &qmlObjectNode, const QString &/*propertyName*/)
{
QmlItemNode itemNode = qmlObjectNode.toQmlItemNode();
if (itemNode.isValid() && scene()->hasItemForQmlItemNode(itemNode)) {
@@ -523,7 +523,7 @@ void FormEditorView::parentChanged(const QmlObjectNode &qmlObjectNode)
}
}
void FormEditorView::otherPropertyChanged(const QmlObjectNode &qmlObjectNode)
void FormEditorView::otherPropertyChanged(const QmlObjectNode &qmlObjectNode, const QString &/*propertyName*/)
{
Q_ASSERT(qmlObjectNode.isValid());
@@ -546,19 +546,6 @@ void FormEditorView::setSelectOnlyContentItemsAction(bool selectOnlyContentItems
m_selectionTool->setSelectOnlyContentItems(selectOnlyContentItems);
}
void FormEditorView::updateItem(const QmlObjectNode &qmlObjectNode)
{
Q_ASSERT(qmlObjectNode.isValid());
QmlItemNode itemNode = findRecursiveQmlItemNode(qmlObjectNode);
if (itemNode.isValid() && scene()->hasItemForQmlItemNode(itemNode)) {
m_scene->synchronizeOtherProperty(itemNode);
m_currentTool->formEditorItemsChanged(QList<FormEditorItem*>() << m_scene->itemForQmlItemNode(itemNode));
}
}
void FormEditorView::stateChanged(const QmlModelState &newQmlModelState, const QmlModelState &oldQmlModelState)
{
QmlModelView::stateChanged(newQmlModelState, oldQmlModelState);

View File

@@ -32,8 +32,10 @@
#include <qmlmodelview.h>
QT_BEGIN_NAMESPACE
class QGraphicsScene;
class QGraphicsSceneMouseEvent;
QT_END_NAMESPACE
namespace QmlDesigner {
@@ -108,10 +110,9 @@ signals:
void ItemCreatorDeActivated();
protected:
void transformChanged(const QmlObjectNode &qmlObjectNode);
void transformChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName);
void parentChanged(const QmlObjectNode &qmlObjectNode);
void otherPropertyChanged(const QmlObjectNode &qmlObjectNode);
void updateItem(const QmlObjectNode &qmlObjectNode);
void otherPropertyChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName);
void stateChanged(const QmlModelState &newQmlModelState, const QmlModelState &oldQmlModelState);
protected slots:

View File

@@ -32,7 +32,9 @@
#include <QWidget>
QT_BEGIN_NAMESPACE
class QActionGroup;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,7 +32,9 @@
#include <QWidgetAction>
QT_BEGIN_NAMESPACE
class QStandardItemModel;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,7 +32,9 @@
#include "formeditoritem.h"
QT_BEGIN_NAMESPACE
class QLineF;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,7 +32,9 @@
#include <QWidget>
QT_BEGIN_NAMESPACE
class QToolBar;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,7 +32,9 @@
#include <QWidgetAction>
QT_BEGIN_NAMESPACE
class QAbstractItemModel;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -33,7 +33,9 @@
#include <QWidgetAction>
#include <QWeakPointer>
QT_BEGIN_NAMESPACE
class QComboBox;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -35,7 +35,9 @@
#include <QStringList>
QT_BEGIN_NAMESPACE
class QStandardItemModel;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -35,12 +35,14 @@
#include <QtCore/QObject>
#include <QtCore/QString>
QT_BEGIN_NAMESPACE
class QUndoStack;
class QWidget;
class QIODevice;
class QProcess;
class QPlainTextEdit;
class QmlError;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,8 +32,10 @@
#include <QtCore/QObject>
QT_BEGIN_NAMESPACE
class QWidget;
class QDialog;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,7 +32,9 @@
#include <QTimeLine>
#include <QDrag>
QT_BEGIN_NAMESPACE
class QMimeData;
QT_END_NAMESPACE
namespace QmlDesigner {
@@ -119,6 +121,11 @@ class CustomItemLibraryDrag : public QDrag {
void exec()
{ QmlDesignerItemLibraryDragAndDrop::CustomDragAndDrop::startCustomDrag(m_pixmap, m_preview, m_mimeData); }
public slots:
void stopDrag() {
QmlDesignerItemLibraryDragAndDrop::CustomDragAndDrop::endCustomDrag();
}
private:
QPixmap m_pixmap, m_preview;
QMimeData *m_mimeData;

View File

@@ -52,6 +52,11 @@
#include <QFile>
#include <QDirModel>
#include <QFileIconProvider>
#include <QImageReader>
#include <QmlView>
#include <QmlGraphicsItem>
#include <private/qmlengine_p.h>
namespace QmlDesigner {
@@ -59,119 +64,127 @@ namespace QmlDesigner {
class MyFileIconProvider : public QFileIconProvider
{
public:
MyFileIconProvider() : QFileIconProvider()
MyFileIconProvider(const QSize &iconSize)
: QFileIconProvider(),
m_iconSize(iconSize)
{}
virtual QIcon icon ( const QFileInfo & info ) const
{
QPixmap pixmap(info.absoluteFilePath());
if (pixmap.isNull())
return QFileIconProvider::icon(info);
else return pixmap; //pixmap.scaled(128, 128, Qt::KeepAspectRatio);
if (pixmap.isNull()) {
QIcon defaultIcon(QFileIconProvider::icon(info));
pixmap = defaultIcon.pixmap(defaultIcon.actualSize(m_iconSize));
}
if (pixmap.width() == m_iconSize.width()
&& pixmap.height() == m_iconSize.height())
return pixmap;
if ((pixmap.width() > m_iconSize.width())
|| (pixmap.height() > m_iconSize.height()))
return pixmap.scaled(m_iconSize, Qt::KeepAspectRatio);
QPoint offset((m_iconSize.width() - pixmap.width()) / 2,
(m_iconSize.height() - pixmap.height()) / 2);
QImage newIcon(m_iconSize, QImage::Format_ARGB32_Premultiplied);
newIcon.fill(Qt::transparent);
QPainter painter(&newIcon);
painter.drawPixmap(offset, pixmap);
return QPixmap::fromImage(newIcon);
}
};
class GrabHelper {
Q_DISABLE_COPY(GrabHelper)
public:
GrabHelper();
QPixmap grabItem(QGraphicsItem *item);
private:
QGraphicsScene m_scene;
QGraphicsView m_view;
QSize m_iconSize;
};
GrabHelper::GrabHelper()
{
m_view.setScene(&m_scene);
m_view.setFrameShape(QFrame::NoFrame);
m_view.setAlignment(Qt::AlignLeft|Qt::AlignTop);
m_view.setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
m_view.setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
}
QPixmap GrabHelper::grabItem(QGraphicsItem *item)
{
if (item->scene()) {
qWarning("%s: WARNING: Attempt to grab item that is part of another scene!", Q_FUNC_INFO);
return QPixmap();
}
// Temporarily add the item, resize the view widget and grab it.
m_scene.addItem(item);
item->setPos(0.0, 0.0);
const QSize size = item->boundingRect().size().toSize();
QPixmap rc;
if (!size.isEmpty()) { // We have seen horses barf...
m_view.resize(size);
rc = QPixmap::grabWidget(&m_view);
}
m_scene.removeItem(item);
return rc;
}
// ---------- ItemLibraryPrivate
class ItemLibraryPrivate {
public:
ItemLibraryPrivate(QObject *object);
~ItemLibraryPrivate();
Ui::ItemLibrary m_ui;
Internal::ItemLibraryModel *m_itemLibraryModel;
QmlView *m_itemsView;
QDirModel *m_resourcesDirModel;
QSortFilterProxyModel *m_filterProxy;
GrabHelper *m_grabHelper;
QString m_resourcePath;
QSize m_itemIconSize, m_resIconSize;
MyFileIconProvider m_iconProvider;
};
ItemLibraryPrivate::ItemLibraryPrivate(QObject *object) :
m_itemLibraryModel(0),
m_grabHelper(0)
m_itemsView(0),
m_itemIconSize(32, 32),
m_resIconSize(32, 32),
m_iconProvider(m_resIconSize)
{
m_resourcePath = QDir::currentPath();
Q_UNUSED(object);
}
ItemLibraryPrivate::~ItemLibraryPrivate()
{
delete m_grabHelper;
}
ItemLibrary::ItemLibrary(QWidget *parent) :
QFrame(parent),
m_d(new ItemLibraryPrivate(this))
{
m_d->m_ui.setupUi(this);
m_d->m_itemLibraryModel = new Internal::ItemLibraryModel(this);
layout()->setContentsMargins(3, 3, 3, 3);
layout()->setSpacing(3);
m_d->m_resourcesDirModel = new QDirModel(this);
m_d->m_filterProxy = new QSortFilterProxyModel(this);
m_d->m_filterProxy->setSourceModel(m_d->m_itemLibraryModel);
m_d->m_ui.ItemLibraryTreeView->setModel(m_d->m_filterProxy);
m_d->m_filterProxy->setDynamicSortFilter(true);
m_d->m_ui.ItemLibraryTreeView->setRealModel(m_d->m_itemLibraryModel);
m_d->m_ui.ItemLibraryTreeView->setIconSize(QSize(64, 64));
m_d->m_ui.ItemLibraryTreeView->setModel(m_d->m_resourcesDirModel);
m_d->m_ui.ItemLibraryTreeView->setIconSize(m_d->m_resIconSize);
m_d->m_ui.ItemLibraryTreeView->setColumnHidden(1, true);
m_d->m_ui.ItemLibraryTreeView->setColumnHidden(2, true);
m_d->m_ui.ItemLibraryTreeView->setColumnHidden(3, true);
m_d->m_ui.ItemLibraryTreeView->setSortingEnabled(true);
m_d->m_ui.ItemLibraryTreeView->setHeaderHidden(true);
m_d->m_ui.ItemLibraryTreeView->setIndentation(10);
m_d->m_ui.ItemLibraryTreeView->setAnimated(true);
m_d->m_ui.ItemLibraryTreeView->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
m_d->m_ui.ItemLibraryTreeView->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
m_d->m_ui.ItemLibraryTreeView->setAttribute(Qt::WA_MacShowFocusRect, false);
m_d->m_filterProxy->setFilterCaseSensitivity(Qt::CaseInsensitive);
m_d->m_filterProxy->setFilterRole(Qt::UserRole);
m_d->m_filterProxy->setSortRole(Qt::DisplayRole);
connect(m_d->m_ui.lineEdit, SIGNAL(textChanged(QString)), m_d->m_filterProxy, SLOT(setFilterRegExp(QString)));
connect(m_d->m_ui.lineEdit, SIGNAL(textChanged(QString)), this, SLOT(setNameFilter(QString)));
connect(m_d->m_ui.lineEdit, SIGNAL(textChanged(QString)), this, SLOT(expandAll()));
connect(m_d->m_ui.buttonItems, SIGNAL(toggled (bool)), this, SLOT(itemLibraryButton()));
connect(m_d->m_ui.buttonResources, SIGNAL(toggled (bool)), this, SLOT(resourcesButton()));
connect(m_d->m_ui.ItemLibraryTreeView, SIGNAL(itemActivated(const QString&)), this, SIGNAL(itemActivated(const QString&)));
m_d->m_ui.lineEdit->setDragEnabled(false);
setNameFilter("");
m_d->m_ui.ItemLibraryTreeView->setRootIndex(m_d->m_resourcesDirModel->index(m_d->m_resourcePath));
MyFileIconProvider *fileIconProvider = new MyFileIconProvider();
m_d->m_resourcesDirModel->setIconProvider(fileIconProvider);
const QString qmlSourcePath(":/ItemLibrary/qml/ItemsView.qml");
QFile qmlSourceFile(qmlSourcePath);
qmlSourceFile.open(QFile::ReadOnly);
Q_ASSERT(qmlSourceFile.isOpen());
QString qmlSource(qmlSourceFile.readAll());
m_d->m_itemsView = new QmlView(this);
m_d->m_itemsView->setQml(qmlSource, qmlSourcePath);
m_d->m_itemsView->setAttribute(Qt::WA_OpaquePaintEvent);
m_d->m_itemsView->setAttribute(Qt::WA_NoSystemBackground);
m_d->m_itemsView->setAcceptDrops(false);
m_d->m_itemsView->setFocusPolicy(Qt::ClickFocus);
m_d->m_itemsView->setContentResizable(true);
m_d->m_ui.ItemLibraryGridLayout->addWidget(m_d->m_itemsView, 0, 0);
m_d->m_itemLibraryModel = new Internal::ItemLibraryModel(QmlEnginePrivate::getScriptEngine(m_d->m_itemsView->engine()), this);
m_d->m_itemLibraryModel->setItemIconSize(m_d->m_itemIconSize);
m_d->m_itemsView->rootContext()->setContextProperty(QLatin1String("itemLibraryModel"), m_d->m_itemLibraryModel);
m_d->m_itemsView->rootContext()->setContextProperty(QLatin1String("itemLibraryIconWidth"), m_d->m_itemIconSize.width());
m_d->m_itemsView->rootContext()->setContextProperty(QLatin1String("itemLibraryIconHeight"), m_d->m_itemIconSize.height());
m_d->m_itemsView->execute();
connect(m_d->m_itemsView->root(), SIGNAL(itemSelected(int)), this, SLOT(showItemInfo(int)));
connect(m_d->m_itemsView->root(), SIGNAL(itemDragged(int)), this, SLOT(startDragAndDrop(int)));
connect(this, SIGNAL(expandAllItems()), m_d->m_itemsView->root(), SLOT(expandAll()));
connect(m_d->m_ui.lineEdit, SIGNAL(textChanged(QString)), this, SLOT(setSearchFilter(QString)));
m_d->m_ui.lineEdit->setDragEnabled(false);
connect(m_d->m_ui.buttonItems, SIGNAL(clicked()), this, SLOT(itemLibraryButtonToggled()));
connect(m_d->m_ui.buttonResources, SIGNAL(clicked()), this, SLOT(resourcesButtonToggled()));
m_d->m_ui.buttonItems->setChecked(true);
itemLibraryButtonToggled();
setSearchFilter("");
m_d->m_resourcesDirModel->setIconProvider(&m_d->m_iconProvider);
setWindowTitle(tr("Library", "Title of library view"));
@@ -194,8 +207,6 @@ ItemLibrary::ItemLibrary(QWidget *parent) :
QString styleSheet = QLatin1String(file.readAll());
m_d->m_ui.ItemLibraryTreeView->setStyleSheet(styleSheet);
}
m_d->m_ui.buttonItems->setChecked(true);
}
ItemLibrary::~ItemLibrary()
@@ -203,48 +214,44 @@ ItemLibrary::~ItemLibrary()
delete m_d;
}
void ItemLibrary::setNameFilter(const QString &nameFilter)
{
QStringList nameFilterList;
nameFilterList.append(nameFilter + "*.gif");
nameFilterList.append(nameFilter + "*.png");
nameFilterList.append(nameFilter + "*.jpg");
nameFilterList.append(nameFilter + "*.");
m_d->m_resourcesDirModel->setFilter(QDir::AllDirs | QDir::Files | QDir::NoDotAndDotDot);
m_d->m_resourcesDirModel->setNameFilters(nameFilterList);
if (m_d->m_ui.ItemLibraryTreeView->model() == m_d->m_resourcesDirModel)
m_d->m_ui.ItemLibraryTreeView->setRootIndex(m_d->m_resourcesDirModel->index(m_d->m_resourcePath));
}
void ItemLibrary::itemLibraryButton()
void ItemLibrary::setSearchFilter(const QString &searchFilter)
{
if (m_d->m_ui.buttonItems->isChecked()) {
m_d->m_filterProxy->setSourceModel(m_d->m_itemLibraryModel);
m_d->m_ui.ItemLibraryTreeView->setModel(m_d->m_filterProxy);
m_d->m_ui.ItemLibraryTreeView->setIconSize(QSize(64, 64));
m_d->m_ui.buttonResources->setChecked(false);
m_d->m_ui.ItemLibraryTreeView->setRealModel(m_d->m_itemLibraryModel);
expandAll();
m_d->m_itemLibraryModel->setSearchText(searchFilter);
m_d->m_itemsView->update();
emit expandAllItems();
} else {
QStringList nameFilterList;
if (searchFilter.contains('.')) {
nameFilterList.append(QString("*%1*").arg(searchFilter));
} else {
foreach (const QByteArray &extension, QImageReader::supportedImageFormats()) {
nameFilterList.append(QString("*%1*.%2").arg(searchFilter, QString::fromAscii(extension)));
}
}
m_d->m_resourcesDirModel->setFilter(QDir::AllDirs | QDir::Files | QDir::NoDotAndDotDot);
m_d->m_resourcesDirModel->setNameFilters(nameFilterList);
if (m_d->m_ui.ItemLibraryTreeView->model() == m_d->m_resourcesDirModel)
m_d->m_ui.ItemLibraryTreeView->setRootIndex(m_d->m_resourcesDirModel->index(m_d->m_resourcePath));
m_d->m_ui.ItemLibraryTreeView->expandToDepth(1);
}
}
void ItemLibrary::resourcesButton()
void ItemLibrary::itemLibraryButtonToggled()
{
if (m_d->m_ui.buttonResources->isChecked()) {
m_d->m_ui.ItemLibraryTreeView->setModel(m_d->m_resourcesDirModel);
m_d->m_ui.ItemLibraryTreeView->setIconSize(QSize(32, 32));
m_d->m_ui.buttonItems->setChecked(false);
m_d->m_ui.ItemLibraryTreeView->setRootIndex(m_d->m_resourcesDirModel->index(m_d->m_resourcePath));
m_d->m_ui.ItemLibraryTreeView->setColumnHidden(1, true);
m_d->m_ui.ItemLibraryTreeView->setColumnHidden(2, true);
m_d->m_ui.ItemLibraryTreeView->setColumnHidden(3, true);
expandAll();
}
m_d->m_ui.LibraryStackedWidget->setCurrentIndex(0);
m_d->m_ui.buttonItems->setChecked(true);
m_d->m_ui.buttonResources->setChecked(false);
setSearchFilter(m_d->m_ui.lineEdit->text());
}
void ItemLibrary::addItemLibraryInfo(const ItemLibraryInfo &itemLibraryInfo)
void ItemLibrary::resourcesButtonToggled()
{
m_d->m_itemLibraryModel->addItemLibraryInfo(itemLibraryInfo);
m_d->m_ui.LibraryStackedWidget->setCurrentIndex(1);
m_d->m_ui.buttonResources->setChecked(true);
m_d->m_ui.buttonItems->setChecked(false);
setSearchFilter(m_d->m_ui.lineEdit->text());
}
void ItemLibrary::setResourcePath(const QString &resourcePath)
@@ -252,70 +259,30 @@ void ItemLibrary::setResourcePath(const QString &resourcePath)
m_d->m_resourcePath = resourcePath;
}
void ItemLibrary::startDragAndDrop(int itemLibId)
{
QMimeData *mimeData = m_d->m_itemLibraryModel->getMimeData(itemLibId);
CustomItemLibraryDrag *drag = new CustomItemLibraryDrag(this);
const QImage image = qvariant_cast<QImage>(mimeData->imageData());
drag->setPixmap(m_d->m_itemLibraryModel->getIcon(itemLibId).pixmap(32, 32));
drag->setPreview(QPixmap::fromImage(image));
drag->setMimeData(mimeData);
connect(m_d->m_itemsView->root(), SIGNAL(stopDragAndDrop()), drag, SLOT(stopDrag()));
drag->exec();
}
void ItemLibrary::showItemInfo(int /*itemLibId*/)
{
// qDebug() << "showing item info about id" << itemLibId;
}
void ItemLibrary::setMetaInfo(const MetaInfo &metaInfo)
{
m_d->m_itemLibraryModel->clear();
foreach (const QString &type, metaInfo.itemLibraryItems()) {
NodeMetaInfo nodeInfo = metaInfo.nodeMetaInfo(type);
QList<ItemLibraryInfo> itemLibraryRepresentationList = metaInfo.itemLibraryRepresentations(nodeInfo);
if (!metaInfo.hasNodeMetaInfo(type))
qWarning() << "ItemLibrary: type not declared: " << type;
if (!itemLibraryRepresentationList.isEmpty() && metaInfo.hasNodeMetaInfo(type)) {
foreach (ItemLibraryInfo itemLibraryRepresentation, itemLibraryRepresentationList) {
QImage image(64, 64, QImage::Format_RGB32); // = m_d->m_queryView->paintObject(nodeInfo, itemLibraryRepresentation.properties()); TODO
image.fill(0xffffffff);
if (!image.isNull()) {
QPainter p(&image);
QPen pen(Qt::gray);
pen.setWidth(2);
p.setPen(pen);
p.drawRect(1, 1, image.width() - 2, image.height() - 2);
}
QIcon icon = itemLibraryRepresentation.icon();
if (itemLibraryRepresentation.icon().isNull())
itemLibraryRepresentation.setIcon(QIcon(":/ItemLibrary/images/default-icon.png"));
if (itemLibraryRepresentation.category().isEmpty())
itemLibraryRepresentation.setCategory(nodeInfo.category());
if (!image.isNull()) {
itemLibraryRepresentation.setDragIcon(QPixmap::fromImage(image));
addItemLibraryInfo(itemLibraryRepresentation);
}
}
} else {
QImage image; // = m_d->m_queryView->paintObject(nodeInfo); TODO we have to render image
QIcon icon = nodeInfo.icon();
if (icon.isNull())
icon = QIcon(":/ItemLibrary/images/default-icon.png");
ItemLibraryInfo itemLibraryInfo;
itemLibraryInfo.setName(type);
itemLibraryInfo.setTypeName(nodeInfo.typeName());
itemLibraryInfo.setCategory(nodeInfo.category());
itemLibraryInfo.setIcon(icon);
itemLibraryInfo.setMajorVersion(nodeInfo.majorVersion());
itemLibraryInfo.setMinorVersion(nodeInfo.minorVersion());
itemLibraryInfo.setDragIcon(QPixmap::fromImage(image));
addItemLibraryInfo(itemLibraryInfo);
}
}
expandAll();
}
void ItemLibrary::expandAll()
{
m_d->m_ui.ItemLibraryTreeView->expandToDepth(1);
}
void ItemLibrary::contextMenuEvent (QContextMenuEvent *event)
{
event->accept();
QMenu menu;
menu.addAction(tr("About plugins..."));
menu.exec(event->globalPos());
m_d->m_itemLibraryModel->update(metaInfo);
}
}

View File

@@ -32,9 +32,11 @@
#include <QtGui/QFrame>
QT_BEGIN_NAMESPACE
class QGraphicsItem;
class QPixmap;
class QMimeData;
QT_END_NAMESPACE
namespace QmlDesigner {
@@ -46,6 +48,7 @@ class ItemLibrary : public QFrame
{
Q_OBJECT
Q_DISABLE_COPY(ItemLibrary)
public:
ItemLibrary(QWidget *parent = 0);
virtual ~ItemLibrary();
@@ -53,28 +56,25 @@ public:
void addItemLibraryInfo(const ItemLibraryInfo &ItemLibraryInfo);
void setMetaInfo(const MetaInfo &metaInfo);
// Helper for creating widget box items. Note that this temporarily
// adds the item to a scene, so, the item must not be associated
// with a scene.
public Q_SLOTS:
void expandAll();
void itemLibraryButton();
void resourcesButton();
void setNameFilter(const QString &nameFilter);
void itemLibraryButtonToggled();
void resourcesButtonToggled();
void setSearchFilter(const QString &nameFilter);
void setResourcePath(const QString &resourcePath);
void startDragAndDrop(int itemLibId);
void showItemInfo(int itemLibId);
signals:
void itemActivated(const QString& itemName);
protected:
virtual void contextMenuEvent (QContextMenuEvent * event);
void expandAllItems();
private:
ItemLibraryPrivate *m_d;
};
//class ItemLibraryFilter : public QObject
}
#endif // ITEMLIBRARY_H

View File

@@ -6,7 +6,8 @@ VPATH += $$PWD
INCLUDEPATH += $$PWD
# Input
HEADERS += itemlibrary.h itemlibrarymodel.h customdraganddrop.h
HEADERS += itemlibrary.h customdraganddrop.h itemlibrarymodel.h itemlibrarytreeview.h
FORMS += itemlibrary.ui
SOURCES += itemlibrary.cpp itemlibrarymodel.cpp customdraganddrop.cpp
SOURCES += itemlibrary.cpp customdraganddrop.cpp itemlibrarymodel.cpp itemlibrarytreeview.cpp
RESOURCES += itemlibrary.qrc

View File

@@ -1,5 +1,13 @@
<RCC>
<qresource prefix="/ItemLibrary/images" >
<file>default-icon.png</file>
<qresource prefix="/ItemLibrary" >
<file>qml/ItemsView.qml</file>
<file>qml/ItemsViewStyle.qml</file>
<file>qml/SectionView.qml</file>
<file>qml/ItemView.qml</file>
<file>qml/Scrollbar.qml</file>
<file>qml/Selector.qml</file>
<file>images/item-default-icon.png</file>
</qresource>
</RCC>

View File

@@ -7,104 +7,220 @@
<x>0</x>
<y>0</y>
<width>497</width>
<height>792</height>
<height>635</height>
</rect>
</property>
<property name="windowTitle">
<string>ItemLibrary</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<property name="leftMargin">
<number>2</number>
</property>
<property name="topMargin">
<number>6</number>
</property>
<property name="rightMargin">
<number>2</number>
</property>
<property name="bottomMargin">
<number>2</number>
</property>
<property name="horizontalSpacing">
<number>4</number>
</property>
<item row="0" column="0">
<spacer name="horizontalSpacer_2">
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<layout class="QHBoxLayout" name="horizontalLayout_2">
<item>
<spacer name="horizontalSpacer">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>6</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="buttonItems">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>80</width>
<height>30</height>
</size>
</property>
<property name="text">
<string>Items</string>
</property>
<property name="checkable">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<spacer name="horizontalSpacer_4">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>6</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="buttonResources">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>80</width>
<height>30</height>
</size>
</property>
<property name="text">
<string>Resources</string>
</property>
<property name="checkable">
<bool>true</bool>
</property>
<property name="checked">
<bool>false</bool>
</property>
<property name="autoExclusive">
<bool>false</bool>
</property>
</widget>
</item>
<item>
<spacer name="horizontalSpacer_5">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>6</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item>
<widget class="Line" name="line_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Fixed</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>6</width>
<height>27</height>
</size>
</property>
</spacer>
</item>
<item row="0" column="1">
<widget class="QLabel" name="label">
<property name="text">
<string>Filter: </string>
</property>
</widget>
</item>
<item row="0" column="2">
<widget class="QLineEdit" name="lineEdit"/>
<item>
<layout class="QHBoxLayout" name="horizontalLayout">
<item>
<spacer name="horizontalSpacer_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Fixed</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>6</width>
<height>6</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QLabel" name="label">
<property name="text">
<string>Filter: </string>
</property>
</widget>
</item>
<item>
<widget class="QLineEdit" name="lineEdit"/>
</item>
<item>
<spacer name="horizontalSpacer_3">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Fixed</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>6</width>
<height>6</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item row="0" column="3">
<widget class="QToolButton" name="buttonItems">
<property name="minimumSize">
<size>
<width>80</width>
<height>30</height>
</size>
</property>
<property name="text">
<string>Items</string>
</property>
<property name="checkable">
<bool>true</bool>
</property>
</widget>
</item>
<item row="0" column="4">
<widget class="QToolButton" name="buttonResources">
<property name="minimumSize">
<size>
<width>80</width>
<height>30</height>
</size>
</property>
<property name="text">
<string>Resources</string>
</property>
<property name="checkable">
<bool>true</bool>
</property>
<property name="checked">
<bool>false</bool>
</property>
<property name="autoExclusive">
<bool>false</bool>
</property>
</widget>
</item>
<item row="1" column="0" colspan="5">
<item>
<widget class="Line" name="line">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
</widget>
</item>
<item row="2" column="0" colspan="5">
<widget class="QmlDesigner::Internal::ItemLibraryTreeView" name="ItemLibraryTreeView">
<property name="enabled">
<bool>true</bool>
<item>
<widget class="QStackedWidget" name="LibraryStackedWidget">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="currentIndex">
<number>1</number>
</property>
<widget class="QWidget" name="page_3">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<layout class="QGridLayout" name="gridLayout_3">
<item row="0" column="0">
<layout class="QGridLayout" name="ItemLibraryGridLayout"/>
</item>
</layout>
</widget>
<widget class="QWidget" name="page_4">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<layout class="QGridLayout" name="gridLayout_2">
<item row="0" column="0">
<layout class="QGridLayout" name="gridLayout_5">
<item row="0" column="0">
<widget class="QmlDesigner::Internal::ItemLibraryTreeView" name="ItemLibraryTreeView">
<property name="enabled">
<bool>true</bool>
</property>
</widget>
</item>
</layout>
</item>
</layout>
</widget>
</widget>
</item>
</layout>
@@ -114,7 +230,7 @@
<customwidget>
<class>QmlDesigner::Internal::ItemLibraryTreeView</class>
<extends>QTreeView</extends>
<header>itemlibrarymodel.h</header>
<header>itemlibrarytreeview.h</header>
</customwidget>
</customwidgets>
<resources/>

View File

@@ -1,297 +1,460 @@
/**************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** Commercial Usage
**
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
**
** GNU Lesser General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** If you are unsure which license is appropriate for your use, please
** contact the sales department at http://qt.nokia.com/contact.
**
**************************************************************************/
#include "itemlibrarymodel.h"
#include "itemlibrary.h"
#include "customdraganddrop.h"
#include "metainfo.h"
#include <QtCore/QMimeData>
#include <QtCore/QDebug>
#include <QtGui/QImage>
#include <QtGui/QPixmap>
#include <QtGui/QDrag>
#include <QSortFilterProxyModel>
#include <QVariant>
#include <QMimeData>
#include <QPainter>
#include <QLabel>
#include <itemlibraryinfo.h>
#include <QDirModel>
enum { debug = 0 };
// Store data and a type enumeration along with the QStandardItem
enum ItemType { CategoryItem, WidgetItem };
enum Roles { TypeRole = Qt::UserRole + 1,
DataRole = Qt::UserRole + 2,
DragPixmapRole = Qt::UserRole + 3};
static inline ItemType itemType(const QStandardItem *item)
{
return static_cast<ItemType>(item->data(TypeRole).toInt());
}
static inline QmlDesigner::ItemLibraryInfo widgetItemData(const QStandardItem *item)
{
const QVariant data = item->data(DataRole);
if (!data.isValid())
return QmlDesigner::ItemLibraryInfo();
return qvariant_cast<QmlDesigner::ItemLibraryInfo>(data);
}
#include <QPen>
#include <qdebug.h>
namespace QmlDesigner {
namespace Internal {
// Cache a drag pixmap on the icon using the DragPixmapRole data field.
static QImage cachedDragImage(const ItemLibraryInfo &ItemLibraryInfo,
QStandardItem *item)
{
const QVariant cached = item->data(DragPixmapRole);
if (cached.type() != QVariant::Invalid)
return qvariant_cast<QImage>(cached);
// TODO: Grab using factory
const QIcon icon = ItemLibraryInfo.dragIcon();
if (icon.isNull())
return QImage();
const QList<QSize> sizes = icon.availableSizes();
if (sizes.isEmpty())
return QImage();
const QImage image = icon.pixmap(sizes.front()).toImage();
item->setData(image, DragPixmapRole);
return image;
}
ItemLibraryModel::ItemLibraryModel(QObject *parent) :
QStandardItemModel(parent)
template <class T>
ItemLibrarySortedModel<T>::ItemLibrarySortedModel(QObject *parent) :
QmlListModel(parent)
{
setSupportedDragActions(Qt::CopyAction);
}
static inline QStandardItem *categoryToItem(const QString &g)
{
QStandardItem *rc = new QStandardItem(g);
rc->setFlags(Qt::ItemIsEnabled);
rc->setData(QVariant(CategoryItem), TypeRole);
rc->setData(g, Qt::UserRole);
return rc;
}
static QStandardItem *customWidgetDataToItem(const ItemLibraryInfo &ItemLibraryInfo)
template <class T>
ItemLibrarySortedModel<T>::~ItemLibrarySortedModel()
{
QStandardItem *item = new QStandardItem(ItemLibraryInfo.name());
const QIcon icon = ItemLibraryInfo.icon();
if (!icon.isNull() && !icon.availableSizes().empty()) {
item->setIcon(icon);
if (icon.availableSizes().count() == 1) {
item->setSizeHint(icon.availableSizes().first() + QSize(1, 1));
clearElements();
}
template <class T>
void ItemLibrarySortedModel<T>::clearElements()
{
while (m_elementOrder.count() > 0)
removeElement(m_elementOrder.at(0).libId);
}
template <class T>
void ItemLibrarySortedModel<T>::addElement(T *element, int libId)
{
struct order_struct orderEntry;
orderEntry.libId = libId;
orderEntry.visible = false;
int pos = 0;
while ((pos < m_elementOrder.count()) &&
(*(m_elementModels.value(m_elementOrder.at(pos).libId)) < *element))
++pos;
m_elementModels.insert(libId, element);
m_elementOrder.insert(pos, orderEntry);
setElementVisible(libId, true);
}
template <class T>
void ItemLibrarySortedModel<T>::removeElement(int libId)
{
T *element = m_elementModels.value(libId);
int pos = findElement(libId);
struct order_struct orderEntry = m_elementOrder.at(pos);
setElementVisible(libId, false);
m_elementModels.remove(libId);
m_elementOrder.removeAt(pos);
delete element;
}
template <class T>
bool ItemLibrarySortedModel<T>::elementVisible(int libId) const
{
int pos = findElement(libId);
return m_elementOrder.at(pos).visible;
}
template <class T>
void ItemLibrarySortedModel<T>::setElementVisible(int libId, bool visible)
{
int pos = findElement(libId),
offset = 0;
if (m_elementOrder.at(pos).visible == visible)
return;
for (int i = 0; (i + offset) < pos;) {
if (m_elementOrder.at(i + offset).visible)
++i;
else
++offset;
}
if (visible)
insert(pos - offset, *(m_elementModels.value(libId)));
else
remove(pos - offset);
m_elementOrder[pos].visible = visible;
}
template <class T>
const QMap<int, T *> &ItemLibrarySortedModel<T>::elements() const
{
return m_elementModels;
}
template <class T>
T *ItemLibrarySortedModel<T>::elementModel(int libId)
{
return m_elementModels.value(libId);
}
template <class T>
int ItemLibrarySortedModel<T>::findElement(int libId) const
{
int i = 0;
QListIterator<struct order_struct> it(m_elementOrder);
while (it.hasNext()) {
if (it.next().libId == libId)
return i;
++i;
}
return -1;
}
ItemLibraryItemModel::ItemLibraryItemModel(QScriptEngine *scriptEngine, int itemLibId, const QString &itemName)
: QScriptValue(scriptEngine->newObject()),
m_scriptEngine(scriptEngine),
m_libId(itemLibId),
m_name(itemName),
m_icon(),
m_iconSize(64, 64)
{
QScriptValue pixmapScriptValue(m_scriptEngine->newVariant(QPixmap()));
setProperty(QLatin1String("itemLibId"), itemLibId);
setProperty(QLatin1String("itemName"), itemName);
setProperty(QLatin1String("itemPixmap"), pixmapScriptValue);
}
ItemLibraryItemModel::~ItemLibraryItemModel()
{
setProperty(QLatin1String("itemPixmap"), QVariant::Invalid);
}
int ItemLibraryItemModel::itemLibId() const
{
return m_libId;
}
QString ItemLibraryItemModel::itemName() const
{
return m_name;
}
void ItemLibraryItemModel::setItemIcon(const QIcon &itemIcon)
{
m_icon = itemIcon;
QScriptValue pixmapScriptValue(m_scriptEngine->newVariant(m_icon.pixmap(m_iconSize)));
setProperty(QLatin1String("itemPixmap"), pixmapScriptValue);
}
void ItemLibraryItemModel::setItemIconSize(const QSize &itemIconSize)
{
m_iconSize = itemIconSize;
// qDebug() << "set icon size" << itemIconSize;
setItemIcon(m_icon);
}
bool ItemLibraryItemModel::operator<(const ItemLibraryItemModel &other) const
{
return itemName() < other.itemName();
}
ItemLibrarySectionModel::ItemLibrarySectionModel(QScriptEngine *scriptEngine, int sectionLibId, const QString &sectionName, QObject *parent)
: QScriptValue(scriptEngine->newObject()),
m_name(sectionName),
m_sectionEntries(parent)
{
QScriptValue::setProperty(QLatin1String("sectionLibId"), sectionLibId);
QScriptValue::setProperty(QLatin1String("sectionName"), sectionName);
QScriptValue::setProperty(QLatin1String("sectionEntries"),
scriptEngine->newVariant(QVariant::fromValue(static_cast<QmlListModel *>(&m_sectionEntries))));
}
QString ItemLibrarySectionModel::sectionName() const
{
return m_name;
}
void ItemLibrarySectionModel::addSectionEntry(ItemLibraryItemModel *sectionEntry)
{
m_sectionEntries.addElement(sectionEntry, sectionEntry->itemLibId());
}
void ItemLibrarySectionModel::removeSectionEntry(int itemLibId)
{
m_sectionEntries.removeElement(itemLibId);
}
bool ItemLibrarySectionModel::updateSectionVisibility(const QString &searchText)
{
bool haveVisibleItems = false;
QMap<int, ItemLibraryItemModel *>::const_iterator itemIt = m_sectionEntries.elements().constBegin();
while (itemIt != m_sectionEntries.elements().constEnd()) {
bool itemVisible = itemIt.value()->itemName().toLower().contains(searchText);
m_sectionEntries.setElementVisible(itemIt.key(), itemVisible);
if (itemVisible)
haveVisibleItems = true;
++itemIt;
}
return haveVisibleItems;
}
void ItemLibrarySectionModel::updateItemIconSize(const QSize &itemIconSize)
{
foreach (ItemLibraryItemModel *item, m_sectionEntries.elements().values()) {
item->setItemIconSize(itemIconSize);
}
}
bool ItemLibrarySectionModel::operator<(const ItemLibrarySectionModel &other) const
{
return sectionName() < other.sectionName();
}
ItemLibraryModel::ItemLibraryModel(QScriptEngine *scriptEngine, QObject *parent)
: ItemLibrarySortedModel<ItemLibrarySectionModel>(parent),
m_scriptEngine(scriptEngine),
m_metaInfo(0),
m_searchText(""),
m_itemIconSize(64, 64),
m_nextLibId(0)
{
}
ItemLibraryModel::~ItemLibraryModel()
{
if (m_metaInfo)
delete m_metaInfo;
}
QString ItemLibraryModel::searchText() const
{
return m_searchText;
}
void ItemLibraryModel::setSearchText(const QString &searchText)
{
QString lowerSearchText = searchText.toLower();
if (m_searchText != lowerSearchText) {
m_searchText = lowerSearchText;
emit searchTextChanged();
updateVisibility();
}
}
void ItemLibraryModel::setItemIconSize(const QSize &itemIconSize)
{
m_itemIconSize = itemIconSize;
foreach (ItemLibrarySectionModel *section, elements().values())
section->updateItemIconSize(itemIconSize);
}
void ItemLibraryModel::update(const MetaInfo &metaInfo)
{
QMap<QString, int> sections;
clearElements();
m_itemInfos.clear();
if (!m_metaInfo) {
m_metaInfo = new MetaInfo(metaInfo);
} else {
*m_metaInfo = metaInfo;
}
foreach (const QString &type, metaInfo.itemLibraryItems()) {
foreach (const ItemLibraryInfo &itemLibraryRepresentation, itemLibraryRepresentations(type)) {
QString itemSectionName = itemLibraryRepresentation.category();
ItemLibrarySectionModel *sectionModel;
ItemLibraryItemModel *itemModel;
int itemId = m_nextLibId++, sectionId;
if (sections.contains(itemSectionName)) {
sectionId = sections.value(itemSectionName);
sectionModel = elementModel(sectionId);
} else {
sectionId = m_nextLibId++;
sectionModel = new ItemLibrarySectionModel(m_scriptEngine.data(), sectionId, itemSectionName, this);
addElement(sectionModel, sectionId);
sections.insert(itemSectionName, sectionId);
}
m_itemInfos.insert(itemId, itemLibraryRepresentation);
itemModel = new ItemLibraryItemModel(m_scriptEngine.data(), itemId, itemLibraryRepresentation.name());
itemModel->setItemIcon(itemLibraryRepresentation.icon());
itemModel->setItemIconSize(m_itemIconSize);
sectionModel->addSectionEntry(itemModel);
}
}
item->setFlags(Qt::ItemIsEnabled|Qt::ItemIsDragEnabled|Qt::ItemIsSelectable);
item->setData(qVariantFromValue(ItemLibraryInfo), DataRole);
item->setData(QVariant(WidgetItem), TypeRole);
item->setData(ItemLibraryInfo.name(), Qt::UserRole);
return item;
updateVisibility();
}
void ItemLibraryModel::addItemLibraryInfo(const ItemLibraryInfo &itemLibraryInfo)
QString ItemLibraryModel::getTypeName(int libId)
{
QStandardItem *categoryItem = findCategoryItem(itemLibraryInfo.category());
if (!categoryItem) {
categoryItem = categoryToItem(itemLibraryInfo.category());
appendRow(categoryItem);
return m_itemInfos.value(libId).typeName();
}
QMimeData *ItemLibraryModel::getMimeData(int libId)
{
QMimeData *mimeData = new QMimeData();
QByteArray data;
QDataStream stream(&data, QIODevice::WriteOnly);
stream << m_itemInfos.value(libId);
mimeData->setData(QLatin1String("application/vnd.bauhaus.itemlibraryinfo"), data);
const QIcon icon = m_itemInfos.value(libId).dragIcon();
if (!icon.isNull()) {
const QList<QSize> sizes = icon.availableSizes();
if (!sizes.isEmpty())
mimeData->setImageData(icon.pixmap(sizes.front()).toImage());
}
categoryItem->appendRow(customWidgetDataToItem(itemLibraryInfo));
QString filterList = categoryItem->data(Qt::UserRole).toString();
filterList += itemLibraryInfo.name();
categoryItem->setData(filterList, Qt::UserRole);
}
QStandardItem *ItemLibraryModel::findCategoryItem(const QString &category)
{
const QStandardItem *root = invisibleRootItem();
const int rowCount = root->rowCount();
for (int i = 0 ; i < rowCount; i++) {
QStandardItem *categoryItem = root->child(i, 0);
if (categoryItem->text() == category)
return categoryItem;
}
return 0;
}
Qt::DropActions ItemLibraryModel::supportedDragActions() const
{
return Qt::CopyAction;
}
Qt::DropActions ItemLibraryModel::supportedDropActions() const
{
return Qt::IgnoreAction;
}
QStringList ItemLibraryModel::mimeTypes () const
{
if (debug)
qDebug() << Q_FUNC_INFO;
return QStringList(QLatin1String("text/xml"));
}
QByteArray ItemLibraryInfoToByteArray(const ItemLibraryInfo &ItemLibraryInfo)
{
QByteArray byteArray;
QDataStream stream(&byteArray, QIODevice::WriteOnly);
stream << ItemLibraryInfo;
return byteArray;
}
QMimeData *ItemLibraryModel::mimeData(const QModelIndexList &indexes) const
{
if (debug)
qDebug() << Q_FUNC_INFO << indexes.size();
if (indexes.size() != 1)
return 0;
QStandardItem *item = itemFromIndex (indexes.front());
if (!item || itemType(item) != WidgetItem)
return 0;
QMimeData *mimeData = new QMimeData;
ItemLibraryInfo ItemLibraryInfo(widgetItemData(item));
const QImage image = cachedDragImage(ItemLibraryInfo, item);
if (!image.isNull())
mimeData->setImageData(image);
mimeData->setData("application/vnd.bauhaus.itemlibraryinfo", ItemLibraryInfoToByteArray(ItemLibraryInfo));
mimeData->removeFormat("text/plain");
mimeData->removeFormat(QLatin1String("text/plain"));
return mimeData;
}
ItemLibraryTreeView::ItemLibraryTreeView(QWidget *parent) :
QTreeView(parent)
QIcon ItemLibraryModel::getIcon(int libId)
{
setDragEnabled(true);
setDragDropMode(QAbstractItemView::DragOnly);
connect(this, SIGNAL(clicked(const QModelIndex &)), this, SLOT(activateItem(const QModelIndex &)));
return m_itemInfos.value(libId).icon();
}
// We need to implement startDrag ourselves since we cannot
// otherwise influence drag pixmap and hotspot in the standard
// implementation.
void ItemLibraryTreeView::startDrag(Qt::DropActions /* supportedActions */)
void ItemLibraryModel::updateVisibility()
{
if (debug)
qDebug() << Q_FUNC_INFO;
QMimeData *mimeData = model()->mimeData(selectedIndexes());
if (!mimeData)
return;
QMap<int, ItemLibrarySectionModel *>::const_iterator sectionIt = elements().constBegin();
while (sectionIt != elements().constEnd()) {
if (qobject_cast<QSortFilterProxyModel*>(model())) {
QModelIndex index = qobject_cast<QSortFilterProxyModel*>(model())->mapToSource(selectedIndexes().front());
ItemLibrarySectionModel *sectionModel = sectionIt.value();
QString sectionSearchText = m_searchText;
QStandardItem *item = m_model->itemFromIndex(index);
if (sectionModel->sectionName().toLower().contains(m_searchText))
sectionSearchText = "";
if (!item)
return;
bool sectionVisibility = sectionModel->updateSectionVisibility(sectionSearchText);
setElementVisible(sectionIt.key(), sectionVisibility);
CustomItemLibraryDrag *drag = new CustomItemLibraryDrag(this);
const QImage image = qvariant_cast<QImage>(mimeData->imageData());
drag->setPixmap(item->icon().pixmap(32, 32));
drag->setPreview(QPixmap::fromImage(image));
drag->setMimeData(mimeData);
++sectionIt;
}
drag->exec();
} else {
QDirModel *dirModel = qobject_cast<QDirModel*>(model());
Q_ASSERT(dirModel);
QFileInfo fileInfo = dirModel->fileInfo(selectedIndexes().front());
QPixmap pixmap(fileInfo.absoluteFilePath());
if (!pixmap.isNull()) {
CustomItemLibraryDrag *drag = new CustomItemLibraryDrag(this);
drag->setPreview(pixmap);
drag->setPixmap(QIcon(pixmap).pixmap(128, 128));
QMimeData *mimeData = new QMimeData;
mimeData->setData("application/vnd.bauhaus.libraryresource", fileInfo.absoluteFilePath().toLatin1());
drag->setMimeData(mimeData);
drag->exec();
emit visibilityUpdated();
}
QList<ItemLibraryInfo> ItemLibraryModel::itemLibraryRepresentations(const QString &type)
{
NodeMetaInfo nodeInfo = m_metaInfo->nodeMetaInfo(type);
QList<ItemLibraryInfo> itemLibraryRepresentationList = m_metaInfo->itemLibraryRepresentations(nodeInfo);
QImage dragImage(64, 64, QImage::Format_RGB32); // TODO: draw item drag icon
dragImage.fill(0xffffffff);
QPainter p(&dragImage);
QPen pen(Qt::gray);
pen.setWidth(2);
p.setPen(pen);
p.drawRect(1, 1, dragImage.width() - 2, dragImage.height() - 2);
QPixmap dragPixmap(QPixmap::fromImage(dragImage));
if (!m_metaInfo->hasNodeMetaInfo(type))
qWarning() << "ItemLibrary: type not declared: " << type;
static QIcon defaultIcon(QLatin1String(":/ItemLibrary/images/item-default-icon.png"));
if (itemLibraryRepresentationList.isEmpty() || !m_metaInfo->hasNodeMetaInfo(type)) {
QIcon icon = nodeInfo.icon();
if (icon.isNull())
icon = defaultIcon;
ItemLibraryInfo itemLibraryInfo;
itemLibraryInfo.setName(type);
itemLibraryInfo.setTypeName(nodeInfo.typeName());
itemLibraryInfo.setCategory(nodeInfo.category());
itemLibraryInfo.setIcon(icon);
itemLibraryInfo.setDragIcon(dragPixmap);
itemLibraryInfo.setMajorVersion(nodeInfo.majorVersion());
itemLibraryInfo.setMinorVersion(nodeInfo.minorVersion());
itemLibraryRepresentationList.append(itemLibraryInfo);
}
else {
foreach (ItemLibraryInfo itemLibraryRepresentation, itemLibraryRepresentationList) {
QIcon icon = itemLibraryRepresentation.icon();
if (itemLibraryRepresentation.icon().isNull())
itemLibraryRepresentation.setIcon(defaultIcon);
if (itemLibraryRepresentation.dragIcon().isNull())
itemLibraryRepresentation.setDragIcon(dragPixmap);
if (itemLibraryRepresentation.category().isEmpty())
itemLibraryRepresentation.setCategory(nodeInfo.category());
}
}
}
static ItemLibraryInfo ItemLibraryInfoFromData(const QByteArray &data)
{
QDataStream stream(data);
ItemLibraryInfo itemLibraryInfo;
stream >> itemLibraryInfo;
return itemLibraryInfo;
}
void ItemLibraryTreeView::activateItem( const QModelIndex & /*index*/)
{
QMimeData *mimeData = model()->mimeData(selectedIndexes());
if (!mimeData)
return;
QString name;
if (qobject_cast<QSortFilterProxyModel*>(model())) {
QModelIndex index = qobject_cast<QSortFilterProxyModel*>(model())->mapToSource(selectedIndexes().front());
QStandardItem *item = m_model->itemFromIndex(index);
if (!item)
return;
ItemLibraryInfo itemLibraryInfo = ItemLibraryInfoFromData(mimeData->data("application/vnd.bauhaus.itemlibraryinfo"));
QString type = itemLibraryInfo.name();
name = "item^" + type;
emit itemActivated(name);
} else {
QDirModel *dirModel = qobject_cast<QDirModel*>(model());
Q_ASSERT(dirModel);
QFileInfo fileInfo = dirModel->fileInfo(selectedIndexes().front());
QPixmap pixmap(fileInfo.absoluteFilePath());
if (!pixmap.isNull()) {
name = "image^" + fileInfo.absoluteFilePath();
emit itemActivated(name);
}
}
return itemLibraryRepresentationList;
}
} // namespace Internal
} // namespace QmlDesigner

View File

@@ -1,89 +1,133 @@
/**************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** Commercial Usage
**
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
**
** GNU Lesser General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** If you are unsure which license is appropriate for your use, please
** contact the sales department at http://qt.nokia.com/contact.
**
**************************************************************************/
#ifndef ITEMLIBRARYMODEL_H
#define ITEMLIBRARYMODEL_H
#include <QtGui/QStandardItemModel>
#include <QtGui/QTreeView>
#include <QDrag>
#include <QDebug>
#include <QTimeLine>
#include <QMap>
#include <QIcon>
#include <QVariant>
#include <QScriptEngine>
#include <private/qmllistmodel_p.h>
class QLabel;
class QMimeData;
namespace QmlDesigner {
class MetaInfo;
class ItemLibraryInfo;
namespace Internal {
// QStandardItemModel-based model for the widget box.
class ItemLibraryModel : public QStandardItemModel
{
Q_OBJECT
template <class T>
class ItemLibrarySortedModel: public QmlListModel {
public:
explicit ItemLibraryModel(QObject *parent = 0);
void addItemLibraryInfo(const ItemLibraryInfo &ItemLibraryInfo);
ItemLibrarySortedModel(QObject *parent = 0);
~ItemLibrarySortedModel();
void clearElements();
QStandardItem *findCategoryItem(const QString &category);
void addElement(T *element, int libId);
void removeElement(int libId);
virtual Qt::DropActions supportedDragActions() const;
virtual Qt::DropActions supportedDropActions() const;
bool elementVisible(int libId) const;
void setElementVisible(int libId, bool visible);
virtual QStringList mimeTypes() const;
virtual QMimeData *mimeData(const QModelIndexList &indexes) const;
};
const QMap<int, T *> &elements() const;
// ItemLibraryTreeView with Drag implementation
class ItemLibraryTreeView : public QTreeView {
Q_OBJECT
public:
explicit ItemLibraryTreeView(QWidget *parent = 0);
virtual void startDrag(Qt::DropActions supportedActions);
void setRealModel(QStandardItemModel *model) { m_model = model; }
signals:
void itemActivated(const QString &itemName);
private slots:
void activateItem( const QModelIndex & index);
T *elementModel(int libId);
int findElement(int libId) const;
private:
QPixmap m_smallImage, m_bigImage;
QStandardItemModel *m_model;
struct order_struct {
int libId;
bool visible;
};
QMap<int, T *> m_elementModels;
QList<struct order_struct> m_elementOrder;
};
class ItemLibraryItemModel: public QScriptValue {
public:
ItemLibraryItemModel(QScriptEngine *scriptEngine, int itemLibId, const QString &itemName);
~ItemLibraryItemModel();
int itemLibId() const;
QString itemName() const;
void setItemIcon(const QIcon &itemIcon);
void setItemIconSize(const QSize &itemIconSize);
bool operator<(const ItemLibraryItemModel &other) const;
private:
QWeakPointer<QScriptEngine> m_scriptEngine;
int m_libId;
QString m_name;
QIcon m_icon;
QSize m_iconSize;
};
class ItemLibrarySectionModel: public QScriptValue {
public:
ItemLibrarySectionModel(QScriptEngine *scriptEngine, int sectionLibId, const QString &sectionName, QObject *parent = 0);
QString sectionName() const;
void addSectionEntry(ItemLibraryItemModel *sectionEntry);
void removeSectionEntry(int itemLibId);
bool updateSectionVisibility(const QString &searchText);
void updateItemIconSize(const QSize &itemIconSize);
bool operator<(const ItemLibrarySectionModel &other) const;
private:
QString m_name;
ItemLibrarySortedModel<ItemLibraryItemModel> m_sectionEntries;
};
class ItemLibraryModel: public ItemLibrarySortedModel<ItemLibrarySectionModel> {
Q_OBJECT
Q_PROPERTY(QString searchText READ searchText WRITE setSearchText NOTIFY searchTextChanged)
public:
ItemLibraryModel(QScriptEngine *scriptEngine, QObject *parent = 0);
~ItemLibraryModel();
QString searchText() const;
void update(const MetaInfo &metaInfo);
QString getTypeName(int libId);
QMimeData *getMimeData(int libId);
QIcon getIcon(int libId);
public slots:
void setSearchText(const QString &searchText);
void setItemIconSize(const QSize &itemIconSize);
signals:
void qmlModelChanged();
void searchTextChanged();
void visibilityUpdated();
private:
void updateVisibility();
QList<ItemLibraryInfo> itemLibraryRepresentations(const QString &type);
QWeakPointer<QScriptEngine> m_scriptEngine;
MetaInfo *m_metaInfo;
QMap<int, ItemLibraryInfo> m_itemInfos;
QString m_searchText;
QSize m_itemIconSize;
int m_nextLibId;
};
} // namespace Internal
} // namespace QmlDesigner
#endif // ITEMLIBRARYMODEL_H

View File

@@ -0,0 +1,109 @@
/**************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** Commercial Usage
**
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
**
** GNU Lesser General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** If you are unsure which license is appropriate for your use, please
** contact the sales department at http://qt.nokia.com/contact.
**
**************************************************************************/
#include "itemlibrarytreeview.h"
#include "itemlibrary.h"
#include "customdraganddrop.h"
#include <QtCore/QMimeData>
#include <QtCore/QDebug>
#include <QtGui/QImage>
#include <QtGui/QPixmap>
#include <QtGui/QDrag>
#include <QPainter>
#include <QLabel>
#include <itemlibraryinfo.h>
#include <QDirModel>
enum { debug = 0 };
namespace QmlDesigner {
namespace Internal {
ItemLibraryTreeView::ItemLibraryTreeView(QWidget *parent) :
QTreeView(parent)
{
setDragEnabled(true);
setDragDropMode(QAbstractItemView::DragOnly);
setUniformRowHeights(true);
connect(this, SIGNAL(clicked(const QModelIndex &)), this, SLOT(activateItem(const QModelIndex &)));
}
// We need to implement startDrag ourselves since we cannot
// otherwise influence drag pixmap and hotspot in the standard
// implementation.
void ItemLibraryTreeView::startDrag(Qt::DropActions /* supportedActions */)
{
if (debug)
qDebug() << Q_FUNC_INFO;
QMimeData *mimeData = model()->mimeData(selectedIndexes());
if (!mimeData)
return;
QDirModel *dirModel = qobject_cast<QDirModel*>(model());
Q_ASSERT(dirModel);
QFileInfo fileInfo = dirModel->fileInfo(selectedIndexes().front());
QPixmap pixmap(fileInfo.absoluteFilePath());
if (!pixmap.isNull()) {
CustomItemLibraryDrag *drag = new CustomItemLibraryDrag(this);
drag->setPreview(pixmap);
drag->setPixmap(QIcon(pixmap).pixmap(128, 128));
QMimeData *mimeData = new QMimeData;
mimeData->setData("application/vnd.bauhaus.libraryresource", fileInfo.absoluteFilePath().toLatin1());
drag->setMimeData(mimeData);
drag->exec();
}
}
void ItemLibraryTreeView::activateItem( const QModelIndex & /*index*/)
{
QMimeData *mimeData = model()->mimeData(selectedIndexes());
if (!mimeData)
return;
QString name;
QDirModel *dirModel = qobject_cast<QDirModel*>(model());
Q_ASSERT(dirModel);
QFileInfo fileInfo = dirModel->fileInfo(selectedIndexes().front());
QPixmap pixmap(fileInfo.absoluteFilePath());
if (!pixmap.isNull()) {
name = "image^" + fileInfo.absoluteFilePath();
emit itemActivated(name);
}
}
} // namespace Internal
} // namespace QmlDesigner

View File

@@ -0,0 +1,66 @@
/**************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** Commercial Usage
**
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
**
** GNU Lesser General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** If you are unsure which license is appropriate for your use, please
** contact the sales department at http://qt.nokia.com/contact.
**
**************************************************************************/
#ifndef ITEMLIBRARYTREEVIEW_H
#define ITEMLIBRARYTREEVIEW_H
#include <QtGui/QTreeView>
#include <QtGui/QStandardItemModel>
#include <QDrag>
#include <QDebug>
#include <QTimeLine>
class QLabel;
namespace QmlDesigner {
namespace Internal {
// ItemLibraryTreeView with Drag implementation
class ItemLibraryTreeView : public QTreeView {
Q_OBJECT
public:
explicit ItemLibraryTreeView(QWidget *parent = 0);
virtual void startDrag(Qt::DropActions supportedActions);
signals:
void itemActivated(const QString &itemName);
private slots:
void activateItem( const QModelIndex &index);
};
} // namespace Internal
} // namespace QmlDesigner
#endif // ITEMLIBRARYTREEVIEW_H

View File

@@ -0,0 +1,87 @@
import Qt 4.6
Item {
id: itemView
property var style
width: GridView.view.cellWidth
height: style.cellHeight
signal itemClicked()
signal itemDragged()
Rectangle {
anchors.top: parent.top
anchors.left: parent.left
anchors.right: parent.right
height: 1
color: style.gridLineColor
}
Rectangle {
anchors.bottom: parent.bottom
anchors.bottomMargin: -1
anchors.left: parent.left
anchors.right: parent.right
height: 1
color: style.gridLineColor
}
Rectangle {
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.left: parent.left
width: 1
color: style.gridLineColor
}
Rectangle {
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.bottomMargin: -1
anchors.right: parent.right
anchors.rightMargin: -1
width: 1
color: style.gridLineColor
}
Image {
id: itemIcon
anchors.top: parent.top
anchors.topMargin: style.cellMargin
anchors.horizontalCenter: parent.horizontalCenter
width: itemLibraryIconWidth
height: itemLibraryIconHeight
pixmap: itemPixmap
}
Text {
id: text
anchors.top: itemIcon.bottom
anchors.topMargin: itemView.style.cellSpacing
anchors.horizontalCenter: parent.horizontalCenter
width: style.textWidth
height: style.textHeight
verticalAlignment: "AlignVCenter"
horizontalAlignment: "AlignHCenter"
text: itemName
// workaround: text color not updated when 'style' var finally assigned
color: style.itemNameTextColor
Component.onCompleted: text.color = style.itemNameTextColor
}
MouseRegion {
id: mouseRegion
anchors.fill: parent
onPositionChanged: {
itemDragged();
}
onClicked: {
itemClicked();
}
}
}

View File

@@ -0,0 +1,144 @@
import Qt 4.6
/*
ListModel {
id: libraryModel
ListElement {
sectionTitle: "Section 1"
sectionEntries: [
ListElement { itemLibId: 0; itemName: "Comp"; itemIconPath: "../images/default-icon.png" },
...
]
}
...
}
*/
/* workaround: ListView reports bogus viewportHeight
ListView {
id: itemsView
property string name: "itemsFlickable"
anchors.fill: parent
interactive: false
model: itemsView.model
delegate: sectionDelegate
}
*/
Rectangle {
id: itemsView
signal itemSelected(int itemLibId)
signal itemDragged(int itemLibId)
function expandAll() {
expandAllEntries();
scrollbar.handleBar.y = 0;
}
signal expandAllEntries()
property int entriesPerRow: Math.max(1, Math.floor((itemsFlickable.width - 2) / style.cellWidth))
property int cellWidth: Math.floor((itemsFlickable.width - 2) / entriesPerRow)
property int cellHeight: style.cellHeight
property var style
style: ItemsViewStyle {}
color: style.backgroundColor
/* workaround: without this, a completed drag and drop operation would
result in the drag being continued when QmlView re-gains
focus */
signal stopDragAndDrop
MouseRegion {
anchors.fill: parent
hoverEnabled: true
onEntered: if (!pressed) itemsView.stopDragAndDrop
}
Component {
id: sectionDelegate
SectionView {
id: section
style: itemsView.style
entriesPerRow: itemsView.entriesPerRow
cellWidth: itemsView.cellWidth
cellHeight: itemsView.cellHeight
width: itemsFlickable.width
itemHighlight: selector
onItemSelected: itemsView.itemSelected(itemLibId)
onItemDragged: itemsView.itemDragged(itemLibId)
function focusSelection() {
itemSelection.focusSelection()
}
Connection {
sender: itemsView
signal: "expandAllEntries()"
script: section.expand()
}
}
}
Flickable {
id: itemsFlickable
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.left: parent.left
anchors.right: scrollbar.left
anchors.rightMargin: 6
clip: true
interactive: false
viewportHeight: col.height
onViewportHeightChanged: scrollbar.limitHandle()
Column {
id: col
Repeater {
model: itemLibraryModel
delegate: sectionDelegate
}
}
Selector {
id: selector
z: -1
style: itemsView.style
scrollFlickable: itemsFlickable
onMoveScrollbarHandle: scrollbar.moveHandle(viewportPos)
width: itemsView.cellWidth
height: itemsView.cellHeight
}
}
Scrollbar {
id: scrollbar
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.left: parent.right
anchors.leftMargin: -10
anchors.right: parent.right
scrollFlickable: itemsFlickable
style: itemsView.style
}
}

View File

@@ -0,0 +1,34 @@
import Qt 4.6
Item {
property string backgroundColor: "#707070"
property string raisedBackgroundColor: "#e0e0e0"
property string scrollbarBackgroundColor: "#505050"
property string scrollbarHandleColor: "#303030"
property string itemNameTextColor: "#c0c0c0"
property string sectionTitleTextColor: "#f0f0f0"
property string sectionTitleBackgroundColor: "#909090"
property string gridLineColor: "#a0a0a0"
property int sectionTitleHeight: 20
property int sectionTitleSpacing: 2
property int selectionSectionOffset: sectionTitleHeight + sectionTitleSpacing
property int iconWidth: 32
property int iconHeight: 32
property int textWidth: 80
property int textHeight: 15
property int cellSpacing: 7
property int cellMargin: 10
property int cellWidth: textWidth + 2*cellMargin
property int cellHeight: itemLibraryIconHeight + textHeight + 2*cellMargin + cellSpacing
}

View File

@@ -0,0 +1,151 @@
import Qt 4.6
Item {
id: bar
property var handleBar: handle
property var scrollFlickable
property var style
property bool scrolling: (scrollFlickable.viewportHeight > scrollFlickable.height)
property int scrollHeight: height - handle.height
Binding {
target: scrollFlickable
property: "viewportY"
value: Math.max(0, scrollFlickable.viewportHeight - scrollFlickable.height) *
handle.y / scrollHeight
}
Rectangle {
anchors.fill: parent;
anchors.rightMargin: 1
anchors.bottomMargin: 1
color: "transparent"
border.width: 1;
border.color: "#8F8F8F";
}
function moveHandle(viewportPos) {
var pos;
if (bar.scrollFlickable) {//.visibleArea.yPosition) {
pos = bar.scrollHeight * viewportPos / (bar.scrollFlickable.viewportHeight - bar.scrollFlickable.height);
} else
pos = 0;
// handleMoveAnimation.to = Math.min(bar.scrollHeight, pos)
// handleMoveAnimation.start();
handle.y = Math.min(bar.scrollHeight, pos)
}
function limitHandle() {
// the following "if" is needed to get around NaN when starting up
if (scrollFlickable)
handle.y = Math.min(handle.height * scrollFlickable.visibleArea.yPosition,
scrollHeight);
else
handle.y = 0;
}
/*
NumberAnimation {
id: handleResetAnimation
target: handle
property: "y"
from: handle.y
to: 0
duration: 500
}
*/
Connection {
sender: scrollFlickable
signal: "heightChanged"
script: {
/* since binding loops prevent setting the handle properly,
let's animate it to 0 */
if (scrollFlickable.viewportY > (scrollFlickable.viewportHeight - scrollFlickable.height))
// handleResetAnimation.start()
handle.y = 0
}
}
onScrollFlickableChanged: handle.y = 0
/*
Rectangle {
anchors.fill: parent
anchors.leftMargin: 3
anchors.rightMargin: 3
anchors.topMargin: 2
anchors.bottomMargin: 2
radius: width / 2
color: style.scrollbarBackgroundColor
}
*/
MouseRegion {
anchors.left: parent.left
anchors.right: parent.right
anchors.top: parent.top
anchors.bottom: handle.top
onClicked: {
// handleMoveAnimation.to = Math.max(0, handle.y - 40)
// handleMoveAnimation.start();
handle.y = Math.max(0, handle.y - 40)
}
}
Item {
id: handle
anchors.left: parent.left
anchors.right: parent.right
height: Math.max(width, bar.height * Math.min(1, scrollFlickable.visibleArea.heightRatio))
// radius: width / 2
// color: style.scrollbarHandleColor
Rectangle {
width: parent.height
height: parent.width
y: parent.height
rotation: -90
transformOrigin: Item.TopLeft
gradient: Gradient {
GradientStop { position: 0.0; color: "#C6C6C6" }
GradientStop { position: 1.0; color: "#7E7E7E" }
}
}
MouseRegion {
anchors.fill: parent
drag.target: parent
drag.axis: "YAxis"
drag.minimumY: 0
drag.maximumY: scrollHeight
}
}
MouseRegion {
anchors.left: parent.left
anchors.right: parent.right
anchors.top: handle.bottom
anchors.bottom: parent.bottom
onClicked: {
// handleMoveAnimation.to = Math.min(scrollHeight, handle.y + 40)
// handleMoveAnimation.start();
handle.y = Math.min(scrollHeight, handle.y + 40)
}
}
/*
NumberAnimation {
id: handleMoveAnimation
target: handle
property: "y"
duration: 200
}
*/
}

View File

@@ -0,0 +1,151 @@
import Qt 4.6
Column {
id: sectionView
property var style
property var itemHighlight
property int entriesPerRow
property int cellWidth
property int cellHeight
signal itemSelected(int itemLibId)
signal itemDragged(int itemLibId)
function expand() {
gridFrame.state = "";
}
Component {
id: itemDelegate
ItemView {
id: item
style: sectionView.style
function selectItem() {
itemHighlight.select(sectionView, item, gridFrame.x, -gridView.viewportY);
sectionView.itemSelected(itemLibId);
}
onItemClicked: selectItem()
onItemDragged: {
selectItem();
sectionView.itemDragged(itemLibId);
}
}
}
Rectangle {
width: parent.width
height: style.sectionTitleHeight
color: style.sectionTitleBackgroundColor
radius: 2
Item {
id: arrow
Rectangle { y: 0; x: 0; height: 1; width: 9; color: "#aeaeae" }
Rectangle { y: 1; x: 1; height: 1; width: 7; color: "#aeaeae" }
Rectangle { y: 2; x: 2; height: 1; width: 5; color: "#aeaeae" }
Rectangle { y: 3; x: 3; height: 1; width: 3; color: "#aeaeae" }
Rectangle { y: 4; x: 4; height: 1; width: 1; color: "#aeaeae" }
anchors.left: parent.left
anchors.leftMargin: 5
anchors.verticalCenter: parent.verticalCenter
width: 9
height: 5
transformOrigin: Item.Center
}
Text {
id: text
anchors.verticalCenter: parent.verticalCenter
anchors.left: arrow.right
anchors.leftMargin: 5
text: sectionName
color: style.sectionTitleTextColor
Component.onCompleted: text.color = style.sectionTitleTextColor
}
MouseRegion {
anchors.fill: parent
onClicked: {
if (itemHighlight.visible &&
(itemHighlight.section == sectionView)) {
itemHighlight.unselect();
sectionView.itemSelected(-1);
}
gridFrame.toggleVisibility()
}
}
}
Item { height: 2; width: 1 }
Item {
id: gridFrame
function toggleVisibility() {
state = ((state == "hidden")? "":"hidden")
}
clip: true
width: sectionView.entriesPerRow * sectionView.cellWidth + 1
height: Math.ceil(sectionEntries.count / sectionView.entriesPerRow) * sectionView.cellHeight + 1
anchors.horizontalCenter: parent.horizontalCenter
GridView {
id: gridView
Connection {
sender: itemLibraryModel
signal: "visibilityUpdated()"
script: gridView.positionViewAtIndex(0)
}
anchors.fill: parent
anchors.rightMargin: 1
anchors.bottomMargin: 1
cellWidth: sectionView.cellWidth
cellHeight: sectionView.cellHeight
model: sectionEntries
delegate: itemDelegate
interactive: false
highlightFollowsCurrentItem: false
}
states: [
State {
name: "hidden"
PropertyChanges {
target: gridFrame
height: 0
opacity: 0
}
PropertyChanges {
target: arrow
rotation: -90
}
}
]
/*
transitions: [
Transition {
NumberAnimation {
matchProperties: "x,y,width,height,opacity,rotation"
duration: 200
}
}
]
*/
}
Item { height: 4; width: 1 }
}

View File

@@ -0,0 +1,140 @@
import Qt 4.6
Item {
id: selector
property var style
property var scrollFlickable
signal moveScrollbarHandle(int viewportPos)
visible: false
property var section: null
property var item: null
property int sectionXOffset: 0
property int sectionYOffset: 0
property real staticX: (section && item)? (section.x + item.x + sectionXOffset):0;
property real staticY: (section && item)? (section.y + style.selectionSectionOffset + item.y + sectionYOffset):0;
property bool animateMove: true
Connection {
sender: itemLibraryModel
signal: "visibilityUpdated()"
script: selector.unselectNow()
}
function select(section, item, sectionXOffset, sectionYOffset) {
if (!selector.visible) {
selector.animateMove = false
}
selector.item = item
selector.section = section
selector.sectionXOffset = sectionXOffset
selector.sectionYOffset = sectionYOffset
if (!selector.visible) {
// print("no prev selection");
// selector.opacity = 0
selector.visible = true
// selectAnimation.start();
}
focusSelection();
}
function focusSelection() {
var pos = -1;
if (selector.staticY < scrollFlickable.viewportY)
pos = selector.staticY
else if ((selector.staticY + selector.height) >
(scrollFlickable.viewportY + scrollFlickable.height - 1))
pos = selector.staticY + selector.height - scrollFlickable.height + 1
if (pos >= 0) {
/*
followSelectionAnimation.to = pos
followSelectionAnimation.start()
*/
scrollFlickable.viewportY = pos;
selector.moveScrollbarHandle(pos)
}
}
function unselect() {
// unselectAnimation.start();
unselectNow();
}
function unselectNow() {
selector.section = null
selector.item = null
selector.sectionXOffset = 0
selector.sectionYOffset = 0
selector.visible = false
selector.opacity = 1
}
/*
NumberAnimation {
id: selectAnimation
target: selector
property: "opacity"
from: 0
to: 1
duration: 200
onRunningChanged: {
if (!running)
selector.animateMove = true
}
}
NumberAnimation {
id: unselectAnimation
target: selector
property: "opacity"
from: 1
to: 0
duration: 150
onRunningChanged: {
if (!running)
selector.unselectNow();
}
}
NumberAnimation {
id: followSelectionAnimation
target: scrollFlickable
property: "viewportY"
duration: 200
}
x: SpringFollow {
source: selector.staticX;
spring: selector.animateMove? 3.0:0.0;
damping: 0.35
epsilon: 0.25
}
y: SpringFollow {
source: selector.staticY;
spring: selector.animateMove? 3.0:0.0;
damping: 0.35
epsilon: 0.25
}
*/
x: selector.staticX
y: selector.staticY
Rectangle {
anchors.fill: parent
color: "steelblue"
}
}

View File

@@ -37,10 +37,12 @@
#include <QPainter>
QT_BEGIN_NAMESPACE
class QTreeView;
class QStandardItem;
class QItemSelection;
class QModelIndex;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -34,10 +34,12 @@
#include <QWeakPointer>
QT_BEGIN_NAMESPACE
class QTreeView;
class QStandardItem;
class QItemSelection;
class QModelIndex;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -51,6 +51,8 @@ public:
} // namespace QmlDesigner
QT_BEGIN_NAMESPACE
Q_DECLARE_INTERFACE(QmlDesigner::IPlugin, QMLDESIGNER_PLUGIN_INTERFACE)
QT_END_NAMESPACE
#endif // IPLUGIN_H

View File

@@ -34,9 +34,11 @@
#include <QtCore/QObject>
#include <QtCore/QList>
QT_BEGIN_NAMESPACE
class QString;
class QAbstractItemModel;
class QDialog;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -160,7 +160,6 @@ private:
int mTop, mLeft, mBottom, mRight;
};
QML_DECLARE_TYPE(QBoxLayoutObject);
class QHBoxLayoutObject : public QBoxLayoutObject
{
@@ -168,7 +167,6 @@ Q_OBJECT
public:
QHBoxLayoutObject(QObject *parent=0);
};
QML_DECLARE_TYPE(QHBoxLayoutObject);
class QVBoxLayoutObject : public QBoxLayoutObject
{
@@ -176,11 +174,14 @@ Q_OBJECT
public:
QVBoxLayoutObject(QObject *parent=0);
};
QML_DECLARE_TYPE(QVBoxLayoutObject);
#endif // BASICLAYOUTS_H
QT_END_NAMESPACE
QML_DECLARE_TYPE(QBoxLayoutObject);
QML_DECLARE_TYPE(QHBoxLayoutObject);
QML_DECLARE_TYPE(QVBoxLayoutObject);
QT_END_HEADER

View File

@@ -1109,9 +1109,6 @@ void QGroupBoxDeclarativeUI::animate(int frame)
gb->update();
}
QML_DECLARE_TYPE(QTabObject);
QML_DEFINE_TYPE(Qt,4,6,QTabObject,QTabObject); //### with namespacing, this should just be 'Tab'
class QTabWidgetDeclarativeUI : public QObject
{
Q_OBJECT
@@ -1171,6 +1168,8 @@ public:
{}
};
QT_END_NAMESPACE
QML_DEFINE_EXTENDED_TYPE(Bauhaus,1,0,QWidget,QWidget,QWidgetDeclarativeUI);
//display
@@ -1230,7 +1229,7 @@ QML_DEFINE_EXTENDED_TYPE(Bauhaus,1,0,QMenu,QMenu, QMenuDeclarativeUI)
//QML_DEFINE_TYPE(Bauhaus,1,0,BauhausreeView,BauhausreeView);
//QML_DEFINE_TYPE(Bauhaus,1,0,BauhausableView,BauhausableView);
QML_DECLARE_TYPE(QTabObject);
QML_DEFINE_TYPE(Qt,4,6,QTabObject,QTabObject); //### with namespacing, this should just be 'Tab'
#include "basicwidgets.moc"
QT_END_NAMESPACE

View File

@@ -57,9 +57,6 @@
#include "filewidget.h"
#include "layoutwidget.h"
QT_BEGIN_NAMESPACE
QML_DECLARE_TYPE(QWidget);
//display
@@ -97,12 +94,16 @@ QML_DECLARE_TYPE(QTabWidget);
QML_DECLARE_TYPE(FileWidget);
QML_DECLARE_TYPE(LayoutWidget);
QT_BEGIN_NAMESPACE
class Action : public QAction {
Q_OBJECT
public:
Action(QObject *parent = 0) : QAction(parent) {}
};
QT_END_NAMESPACE
QML_DECLARE_TYPE(QMenu);
QML_DECLARE_TYPE(Action);
@@ -115,6 +116,4 @@ QML_DECLARE_TYPE(Action);
//top-level windows?
QT_END_NAMESPACE
#endif // BASICWIDGETS_H

View File

@@ -39,9 +39,10 @@
#include <qml.h>
#include <propertyeditorvalue.h>
QT_BEGIN_NAMESPACE
class QtColorButton;
class QToolButton;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -35,10 +35,11 @@
#include <qml.h>
QT_BEGIN_NAMESPACE
class QLabel;
class QPushButton;
class QFontDialog;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -351,54 +351,36 @@ void PropertyEditor::changeExpression(const QString &name)
}
}
void PropertyEditor::anyPropertyChanged(const QmlObjectNode &fxObjectNode)
void PropertyEditor::otherPropertyChanged(const QmlObjectNode &fxObjectNode, const QString &propertyName)
{
QmlModelView::otherPropertyChanged(fxObjectNode, propertyName);
if (fxObjectNode.isValid() && m_currentType && fxObjectNode == m_selectedNode && fxObjectNode.currentState().isValid()) {
foreach (const QString &propertyName, fxObjectNode.modelNode().metaInfo().properties(true).keys()) {
if ( propertyName != "id" && propertyName != "objectName") {
AbstractProperty property = fxObjectNode.modelNode().property(propertyName);
if (fxObjectNode == m_selectedNode || QmlObjectNode(m_selectedNode).propertyChangeForCurrentState() == fxObjectNode) {
if ( m_selectedNode.property(property.name()).isBindingProperty() || !m_selectedNode.hasProperty(propertyName))
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).instanceValue(property.name()));
else
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).modelValue(property.name()));
}
}
AbstractProperty property = fxObjectNode.modelNode().property(propertyName);
if (fxObjectNode == m_selectedNode || QmlObjectNode(m_selectedNode).propertyChangeForCurrentState() == fxObjectNode) {
if ( m_selectedNode.property(property.name()).isBindingProperty() || !m_selectedNode.hasProperty(propertyName))
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).instanceValue(property.name()));
else
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).modelValue(property.name()));
}
}
}
void PropertyEditor::geometryPropertyChanged(const QmlObjectNode &fxObjectNode)
void PropertyEditor::transformChanged(const QmlObjectNode &fxObjectNode, const QString &propertyName)
{
QmlModelView::transformChanged(fxObjectNode, propertyName);
if (fxObjectNode.isValid() && m_currentType && fxObjectNode == m_selectedNode && fxObjectNode.currentState().isValid()) {
QStringList geometryProperties;
geometryProperties << "x" << "y" << "width" << "height" << "rotation" << "scale";
foreach (const QString &propertyName, geometryProperties) {
if ( propertyName != "id" && propertyName != "objectName") {
AbstractProperty property = fxObjectNode.modelNode().property(propertyName);
if (fxObjectNode == m_selectedNode || QmlObjectNode(m_selectedNode).propertyChangeForCurrentState() == fxObjectNode) {
if ( m_selectedNode.property(property.name()).isBindingProperty() || !m_selectedNode.hasProperty(propertyName))
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).instanceValue(property.name()));
else
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).modelValue(property.name()));
}
}
AbstractProperty property = fxObjectNode.modelNode().property(propertyName);
if (fxObjectNode == m_selectedNode || QmlObjectNode(m_selectedNode).propertyChangeForCurrentState() == fxObjectNode) {
if ( m_selectedNode.property(property.name()).isBindingProperty() || !m_selectedNode.hasProperty(propertyName))
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).instanceValue(property.name()));
else
m_currentType->setValue(m_selectedNode, property.name(), QmlObjectNode(m_selectedNode).modelValue(property.name()));
}
}
}
void PropertyEditor::otherPropertyChanged(const QmlObjectNode &fxObjectNode)
{
QmlModelView::otherPropertyChanged(fxObjectNode);
anyPropertyChanged(fxObjectNode);
}
void PropertyEditor::transformChanged(const QmlObjectNode &fxObjectNode)
{
QmlModelView::transformChanged(fxObjectNode);
geometryPropertyChanged(fxObjectNode);
}
void PropertyEditor::setQmlDir(const QString &qmlDir)
{
m_qmlDir = qmlDir;

View File

@@ -37,8 +37,10 @@
#include "qmlanchorbindingproxy.h"
QT_BEGIN_NAMESPACE
class QShortcut;
class QStackedWidget;
QT_END_NAMESPACE
namespace QmlDesigner {
@@ -84,10 +86,6 @@ public:
void anyPropertyChanged(const QmlObjectNode &qmlObjectNode);
void geometryPropertyChanged(const QmlObjectNode &fxObjectNode);
void propertiesAboutToBeRemoved(const QList<AbstractProperty>& propertyList);
void variantPropertiesChanged(const QList<VariantProperty>& propertyList, PropertyChangeFlags propertyChange);
@@ -97,8 +95,8 @@ public:
protected:
void timerEvent(QTimerEvent *event);
void otherPropertyChanged(const QmlObjectNode &);
void transformChanged(const QmlObjectNode &qmlObjectNode);
void otherPropertyChanged(const QmlObjectNode &, const QString &propertyName);
void transformChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName);
void setupPane(const QString &typeName);
void stateChanged(const QmlModelState &newQmlModelState, const QmlModelState &oldQmlModelState);

View File

@@ -48,11 +48,11 @@ public:
virtual QLayout *layout() const;
};
QML_DECLARE_TYPE(QLayoutObject);
#endif // QLAYOUTOBJECT_H
QT_END_NAMESPACE
QML_DECLARE_TYPE(QLayoutObject);
QT_END_HEADER
#endif // QLAYOUTOBJECT_H

View File

@@ -63,7 +63,6 @@ private:
QRectF geometry;
QGraphicsLayout *proxy;
};
QML_DECLARE_TYPE(QProxyLayout);
class QProxyLayoutItem : public QObject, public QGraphicsLayoutItem
{
@@ -87,10 +86,12 @@ private:
QRectF geometry;
QGraphicsLayoutItem *other;
};
QML_DECLARE_TYPE(QProxyLayoutItem);
#endif // QPROXYLAYOUTITEM_H
QT_END_NAMESPACE
QML_DECLARE_TYPE(QProxyLayout);
QML_DECLARE_TYPE(QProxyLayoutItem);
QT_END_HEADER

View File

@@ -33,9 +33,11 @@
#include <QtGui/QGroupBox>
#include <QtGui/QPushButton>
QT_BEGIN_NAMESPACE
class QListWidget;
class QVBoxLayout;
class QTableWidget;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -52,13 +52,6 @@ StatesEditorView::StatesEditorView(StatesEditorModel *editorModel, QObject *pare
m_editorModel(editorModel)
{
Q_ASSERT(m_editorModel);
connect(nodeInstanceView(), SIGNAL(instanceRemoved(NodeInstance)), this, SLOT(sceneChanged()));
connect(nodeInstanceView(), SIGNAL(transformPropertyChanged(NodeInstance)), this, SLOT(sceneChanged()));
connect(nodeInstanceView(), SIGNAL(parentPropertyChanged(NodeInstance)), this, SLOT(sceneChanged()));
connect(nodeInstanceView(), SIGNAL(otherPropertyChanged(NodeInstance)), this, SLOT(sceneChanged()));
connect(nodeInstanceView(), SIGNAL(updateItem(NodeInstance)), this, SLOT(sceneChanged()));
}
void StatesEditorView::setCurrentStateSilent(int index)
@@ -304,9 +297,9 @@ void StatesEditorView::stateChanged(const QmlModelState &newQmlModelState, const
m_editorModel->emitChangedToState(m_modelStates.indexOf(newQmlModelState));
}
void StatesEditorView::transformChanged(const QmlObjectNode &qmlObjectNode)
void StatesEditorView::transformChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName)
{
QmlModelView::transformChanged(qmlObjectNode);
QmlModelView::transformChanged(qmlObjectNode, propertyName);
}
void StatesEditorView::parentChanged(const QmlObjectNode &qmlObjectNode)
@@ -314,15 +307,11 @@ void StatesEditorView::parentChanged(const QmlObjectNode &qmlObjectNode)
QmlModelView::parentChanged(qmlObjectNode);
}
void StatesEditorView::otherPropertyChanged(const QmlObjectNode &qmlObjectNode)
void StatesEditorView::otherPropertyChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName)
{
QmlModelView::otherPropertyChanged(qmlObjectNode);
QmlModelView::otherPropertyChanged(qmlObjectNode, propertyName);
}
void StatesEditorView::updateItem(const QmlObjectNode &qmlObjectNode)
{
QmlModelView::updateItem(qmlObjectNode);
}
void StatesEditorView::customNotification(const AbstractView *view, const QString &identifier, const QList<ModelNode> &nodeList, const QList<QVariant> &data)
{

View File

@@ -69,10 +69,9 @@ protected:
// QmlModelView
void stateChanged(const QmlModelState &newQmlModelState, const QmlModelState &oldQmlModelState);
void transformChanged(const QmlObjectNode &qmlObjectNode) ;
void transformChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName);
void parentChanged(const QmlObjectNode &qmlObjectNode);
void otherPropertyChanged(const QmlObjectNode &qmlObjectNode);
void updateItem(const QmlObjectNode &qmlObjectNode);
void otherPropertyChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName);
void customNotification(const AbstractView *view, const QString &identifier, const QList<ModelNode> &nodeList, const QList<QVariant> &data);

View File

@@ -94,7 +94,8 @@ SOURCES += $$PWD/model/abstractview.cpp \
$$PWD/instances/qmltransitionnodeinstance.cpp \
$$PWD/exceptions/rewritingexception.cpp \
$$PWD/instances/nodeinstancemetaobject.cpp \
$$PWD/instances/behaviornodeinstance.cpp
$$PWD/instances/behaviornodeinstance.cpp \
$$PWD/instances/nodeinstancesignalspy.cpp
HEADERS += $$PWD/include/corelib_global.h \
$$PWD/include/abstractview.h \
$$PWD/include/nodeinstanceview.h \
@@ -185,7 +186,8 @@ HEADERS += $$PWD/include/corelib_global.h \
$$PWD/include/customnotifications.h \
$$PWD/include/rewritingexception.h \
$$PWD/instances/nodeinstancemetaobject.h \
$$PWD/instances/behaviornodeinstance.h
$$PWD/instances/behaviornodeinstance.h \
$$PWD/instances/nodeinstancesignalspy.h
DISTFILES += $$PWD/metafile/widget.metafile
RESOURCES += $$PWD/core.qrc
OTHER_FILES += $$PWD/metainfo/gui.metainfo

View File

@@ -35,7 +35,9 @@
#include <QSharedPointer>
#include "corelib_global.h"
QT_BEGIN_NAMESPACE
class QTextStream;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -39,7 +39,9 @@
#include <QObject>
QT_BEGIN_NAMESPACE
class QStyle;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -47,6 +47,8 @@ public:
} // namespace QmlDesigner
QT_BEGIN_NAMESPACE
Q_DECLARE_INTERFACE(QmlDesigner::IWidgetPlugin, QMLDESIGNER_WIDGETPLUGIN_INTERFACE)
QT_END_NAMESPACE
#endif // IWIDGETPLUGIN_H

View File

@@ -38,7 +38,9 @@
#include <import.h>
QT_BEGIN_NAMESPACE
class QUrl;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -36,7 +36,9 @@
#include <QtCore/QMetaType>
#include <QVariant>
QT_BEGIN_NAMESPACE
class QTextStream;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -37,11 +37,13 @@
#include <propertymetainfo.h>
#include <qmlanchors.h>
QT_BEGIN_NAMESPACE
class QPainter;
class QStyleOptionGraphicsItem;
class QmlContext;
class QGraphicsItem;
class QGraphicsTransform;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -41,9 +41,11 @@
#include <modelnode.h>
#include <nodeinstance.h>
QT_BEGIN_NAMESPACE
class QmlEngine;
class QGraphicsScene;
class QGraphicsView;
QT_END_NAMESPACE
namespace QmlDesigner {
@@ -107,18 +109,16 @@ public:
QRectF sceneRect() const;
void setBlockChangeSignal(bool block);
void notifyPropertyChange(const ModelNode &modelNode, const QString &propertyName);
void setQmlModelView(QmlModelView *qmlModelView);
QmlModelView *qmlModelView() const ;
signals:
void instanceRemoved(const NodeInstance &nodeInstance);
void transformPropertyChanged(const NodeInstance &nodeInstance);
void parentPropertyChanged(const NodeInstance &nodeInstance);
void otherPropertyChanged(const NodeInstance &nodeInstance);
void updateItem(const NodeInstance &nodeInstance);
private slots:
void emitOtherPropertyChanged();
void emitParentPropertyChanged();
void emitTransformPropertyChanged();
void emitUpdateItem(QObject *object);
void emitParentChanged(QObject *child);
private: // functions
NodeInstance loadNode(const ModelNode &rootNode, QObject *objectToBeWrapped = 0);
@@ -145,6 +145,8 @@ private: //variables
QWeakPointer<QmlEngine> m_engine;
QWeakPointer<Internal::ChildrenChangeEventFilter> m_childrenChangeEventFilter;
QWeakPointer<QmlModelView> m_qmlModelView;
bool m_blockChangeSignal;
};

View File

@@ -38,7 +38,9 @@
#include "corelib_global.h"
#include "invalidmetainfoexception.h"
QT_BEGIN_NAMESPACE
class QmlContext;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -88,23 +88,18 @@ public:
void modelAttached(Model *model);
void modelAboutToBeDetached(Model *model);
virtual void nodeInstancePropertyChanged(const ModelNode &node, const QString &propertyName);
protected:
NodeInstance instanceForModelNode(const ModelNode &modelNode);
bool hasInstanceForModelNode(const ModelNode &modelNode);
NodeInstanceView *nodeInstanceView() const;
virtual void transformChanged(const QmlObjectNode &qmlObjectNode) ;
virtual void transformChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName) ;
virtual void parentChanged(const QmlObjectNode &qmlObjectNode);
virtual void otherPropertyChanged(const QmlObjectNode &qmlObjectNode);
virtual void otherPropertyChanged(const QmlObjectNode &qmlObjectNode, const QString &propertyName);
virtual void stateChanged(const QmlModelState &newQmlModelState, const QmlModelState &oldQmlModelState);
virtual void updateItem(const QmlObjectNode &qmlObjectNode);
private slots:
void notifyTransformChanged(const NodeInstance &nodeInstance);
void notifyParentChanged(const NodeInstance &nodeInstance);
void notifyOtherPropertyChanged(const NodeInstance &nodeInstance);
void notifyUpdateItem(const NodeInstance &nodeInstance);
private:
QmlModelState m_state;
};

View File

@@ -33,6 +33,9 @@
#include "corelib_global.h"
#include "abstractproperty.h"
QT_BEGIN_NAMESPACE
class QTextStream;
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -32,7 +32,9 @@
#include "objectnodeinstance.h"
QT_BEGIN_NAMESPACE
class QmlComponent;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -32,7 +32,9 @@
#include "objectnodeinstance.h"
QT_BEGIN_NAMESPACE
class QGraphicsObject;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -181,7 +181,9 @@ NodeInstance NodeInstance::create(NodeInstanceView *nodeInstanceView, const Mode
instance.m_nodeInstance->setModelNode(node);
instance.m_nodeInstance->setNodeInstance(nodeInstanceView);
instance.m_nodeInstance->setNodeInstanceView(nodeInstanceView);
instance.m_nodeInstance->initializePropertyWatcher(instance.m_nodeInstance);
instance.setId(node.id());
@@ -198,7 +200,7 @@ NodeInstance NodeInstance::create(NodeInstanceView *nodeInstanceView, const Mode
NodeInstance NodeInstance::create(NodeInstanceView *nodeInstanceView, const NodeMetaInfo &metaInfo, QmlContext *context)
{
NodeInstance instance(createInstance(metaInfo, context, 0));
instance.m_nodeInstance->setNodeInstance(nodeInstanceView);
instance.m_nodeInstance->setNodeInstanceView(nodeInstanceView);
return instance;
}

View File

@@ -1,11 +1,23 @@
#include "nodeinstancemetaobject.h"
#include "objectnodeinstance.h"
#include <QSharedPointer>
#include <qnumeric.h>
namespace QmlDesigner {
namespace Internal {
NodeInstanceMetaObject::NodeInstanceMetaObject(QObject *object, QmlContext *context)
NodeInstanceMetaObject::NodeInstanceMetaObject(const ObjectNodeInstance::Pointer &nodeInstance)
: QmlOpenMetaObject(nodeInstance->object()),
m_nodeInstance(nodeInstance),
m_context(nodeInstance->modelNode().isRootNode() ? nodeInstance->context() : 0)
{
}
NodeInstanceMetaObject::NodeInstanceMetaObject(const ObjectNodeInstancePointer &nodeInstance, QObject *object, const QString &prefix)
: QmlOpenMetaObject(object),
m_context(context)
m_nodeInstance(nodeInstance),
m_prefix(prefix)
{
}
@@ -14,37 +26,73 @@ void NodeInstanceMetaObject::createNewProperty(const QString &name)
createProperty(name.toLatin1(), 0);
}
int NodeInstanceMetaObject::metaCall(QMetaObject::Call c, int id, void **a)
int NodeInstanceMetaObject::metaCall(QMetaObject::Call call, int id, void **a)
{
if (( c == QMetaObject::ReadProperty || c == QMetaObject::WriteProperty)
int metaCallReturnValue = -1;
if (call == QMetaObject::WriteProperty
&& reinterpret_cast<QVariant *>(a[0])->type() == QVariant::Double
&& qIsNaN(reinterpret_cast<QVariant *>(a[0])->toDouble())) {
return -1;
}
QVariant oldValue;
if (call == QMetaObject::WriteProperty && !property(id).hasNotifySignal())
{
oldValue = property(id).read(m_nodeInstance->object());
}
if (( call == QMetaObject::ReadProperty || call == QMetaObject::WriteProperty)
&& id >= type()->propertyOffset()) {
int propId = id - type()->propertyOffset();
if (c == QMetaObject::ReadProperty) {
if (call == QMetaObject::ReadProperty) {
propertyRead(propId);
*reinterpret_cast<QVariant *>(a[0]) = value(propId);
} else if (c == QMetaObject::WriteProperty) {
} else if (call == QMetaObject::WriteProperty) {
if (value(propId) != *reinterpret_cast<QVariant *>(a[0])) {
propertyWrite(propId);
setValue(propId, *reinterpret_cast<QVariant *>(a[0]));
propertyWritten(propId);
dynamicPropertyWritten(propId);
notifyPropertyChange(id);
activate(object(), type()->signalOffset() + propId, 0);
}
}
return -1;
} else {
if (parent())
return parent()->metaCall(c, id, a);
metaCallReturnValue = parent()->metaCall(call, id, a);
else
return object()->qt_metacall(c, id, a);
metaCallReturnValue = object()->qt_metacall(call, id, a);
if (call == QMetaObject::WriteProperty
&& !property(id).hasNotifySignal()
&& oldValue != property(id).read(m_nodeInstance->object()))
notifyPropertyChange(id);
}
return metaCallReturnValue;
}
void NodeInstanceMetaObject::propertyWritten(int propertyId)
void NodeInstanceMetaObject::dynamicPropertyWritten(int propertyId)
{
if (m_context)
m_context->setContextProperty(name(propertyId), value(propertyId));
}
void NodeInstanceMetaObject::notifyPropertyChange(int id)
{
ObjectNodeInstance::Pointer objectNodeInstance = m_nodeInstance.toStrongRef();
if (objectNodeInstance && objectNodeInstance->nodeInstanceView()) {
if (id < type()->propertyOffset()) {
objectNodeInstance->nodeInstanceView()->notifyPropertyChange(objectNodeInstance->modelNode(), m_prefix + property(id).name());
} else {
objectNodeInstance->nodeInstanceView()->notifyPropertyChange(objectNodeInstance->modelNode(), m_prefix + name(id - type()->propertyOffset()));
}
}
}
} // namespace Internal
} // namespace QmlDesigner

View File

@@ -7,17 +7,25 @@
namespace QmlDesigner {
namespace Internal {
class ObjectNodeInstance;
typedef QSharedPointer<ObjectNodeInstance> ObjectNodeInstancePointer;
typedef QWeakPointer<ObjectNodeInstance> ObjectNodeInstanceWeakPointer;
class NodeInstanceMetaObject : public QmlOpenMetaObject
{
public:
NodeInstanceMetaObject(QObject *object, QmlContext *context);
NodeInstanceMetaObject(const ObjectNodeInstancePointer &nodeInstance);
NodeInstanceMetaObject(const ObjectNodeInstancePointer &nodeInstance, QObject *object, const QString &prefix);
void createNewProperty(const QString &name);
protected:
int metaCall(QMetaObject::Call _c, int _id, void **_a);
void propertyWritten(int);
void dynamicPropertyWritten(int);
void notifyPropertyChange(int id);
private:
ObjectNodeInstanceWeakPointer m_nodeInstance;
QString m_prefix;
QWeakPointer<QmlContext> m_context;
};

View File

@@ -0,0 +1,64 @@
#include "nodeinstancesignalspy.h"
#include <QMetaProperty>
#include <QMetaObject>
#include <QtDebug>
#include <private/qmlmetaproperty_p.h>
#include "objectnodeinstance.h"
#include <QSharedPointer>
namespace QmlDesigner {
namespace Internal {
NodeInstanceSignalSpy::NodeInstanceSignalSpy() :
QObject()
{
}
void NodeInstanceSignalSpy::setObjectNodeInstance(const ObjectNodeInstance::Pointer &nodeInstance)
{
methodeOffset = QObject::staticMetaObject.methodCount() + 1;
registerObject(nodeInstance->object());
m_objectNodeInstance = nodeInstance;
}
void NodeInstanceSignalSpy::registerObject(QObject *spiedObject, const QString &prefix)
{
for (int index = QObject::staticMetaObject.propertyOffset();
index < spiedObject->metaObject()->propertyCount();
index++) {
QMetaProperty metaProperty = spiedObject->metaObject()->property(index);
if (metaProperty.isReadable()
&& !metaProperty.isWritable()
&& QmlMetaType::isQObject(metaProperty.userType())) {
QObject *propertyObject = QmlMetaType::toQObject(metaProperty.read(spiedObject));
registerObject(propertyObject, prefix + metaProperty.name() + ".");
} else if (metaProperty.hasNotifySignal()) {
QMetaMethod metaMethod = metaProperty.notifySignal();
bool isConnecting = QMetaObject::connect(spiedObject, metaMethod.methodIndex(), this, methodeOffset, Qt::DirectConnection);
Q_ASSERT(isConnecting);
m_indexPropertyHash.insert(methodeOffset, prefix + metaProperty.name());
methodeOffset++;
}
}
}
int NodeInstanceSignalSpy::qt_metacall(QMetaObject::Call call, int methodId, void **a)
{
if (call == QMetaObject::InvokeMetaMethod && methodId > QObject::staticMetaObject.methodCount()) {
ObjectNodeInstance::Pointer nodeInstance = m_objectNodeInstance.toStrongRef();
if (nodeInstance && nodeInstance->nodeInstanceView()) {
nodeInstance->nodeInstanceView()->notifyPropertyChange(nodeInstance->modelNode(), m_indexPropertyHash.value(methodId));
}
}
return QObject::qt_metacall(call, methodId, a);
}
} // namespace Internal
} // namespace QmlDesigner

View File

@@ -0,0 +1,36 @@
#ifndef NODEINSTANCESIGNALSPY_H
#define NODEINSTANCESIGNALSPY_H
#include <QObject>
#include <QHash>
#include <QSharedPointer>
namespace QmlDesigner {
namespace Internal {
class ObjectNodeInstance;
typedef QSharedPointer<ObjectNodeInstance> ObjectNodeInstancePointer;
typedef QWeakPointer<ObjectNodeInstance> ObjectNodeInstanceWeakPointer;
class NodeInstanceSignalSpy : public QObject
{
public:
explicit NodeInstanceSignalSpy();
void setObjectNodeInstance(const ObjectNodeInstancePointer &nodeInstance);
virtual int qt_metacall(QMetaObject::Call, int, void **);
protected:
void registerObject(QObject *spiedObject, const QString &prefix = QString());
private:
int methodeOffset;
QHash<int, QString> m_indexPropertyHash;
ObjectNodeInstanceWeakPointer m_objectNodeInstance;
};
} // namespace Internal
} // namespace QmlDesigner
#endif // NODEINSTANCESIGNALSPY_H

View File

@@ -56,6 +56,8 @@
#include "objectnodeinstance.h"
#include "qmlmodelview.h"
enum {
debug = false
};
@@ -459,43 +461,13 @@ NodeInstance NodeInstanceView::rootNodeInstance() const
\see NodeInstance
*/
static bool isTransformProperty(const QString &name)
{
static QStringList transformProperties(QStringList() << "xChanged()"
<< "yChanged()"
<< "zChanged()"
<< "rotationChanged()"
<< "scaleChanged()"
<< "widthChanged()"
<< "heightChanged()"
<< "transformOriginChanged(TransformOrigin)");
return transformProperties.contains(name);
}
void NodeInstanceView::insertInstanceNodeRelationship(const ModelNode &node, const NodeInstance &instance)
{
// connect with every signal of the object to get the formeditor updated
int otherPropertuChangedSlotIndex = staticMetaObject.indexOfSlot("emitOtherPropertyChanged()");
int transformPropertuChangedSlotIndex = staticMetaObject.indexOfSlot("emitTransformPropertyChanged()");
int parentPropertuChangedSlotIndex = staticMetaObject.indexOfSlot("emitParentPropertyChanged()");
for (int index = QObject::staticMetaObject.methodCount();
index < instance.internalObject()->metaObject()->methodCount();
index++) {
QMetaMethod metaMethod = instance.internalObject()->metaObject()->method(index);
if (metaMethod.methodType() == QMetaMethod::Signal) {
if (isTransformProperty(metaMethod.signature())) {
staticMetaObject.connect(instance.internalObject(),index, this, transformPropertuChangedSlotIndex);
} else if (QByteArray(metaMethod.signature()) == QByteArray("parentChanged()")) {
staticMetaObject.connect(instance.internalObject(),index, this, parentPropertuChangedSlotIndex);
} else {
staticMetaObject.connect(instance.internalObject(),index, this, otherPropertuChangedSlotIndex);
}
}
}
instance.internalObject()->installEventFilter(childrenChangeEventFilter());
Q_ASSERT(!m_nodeInstanceHash.contains(node));
m_nodeInstanceHash.insert(node, instance);
m_objectInstanceHash.insert(instance.internalObject(), instance);
@@ -510,7 +482,7 @@ Internal::ChildrenChangeEventFilter *NodeInstanceView::childrenChangeEventFilter
{
if (m_childrenChangeEventFilter.isNull()) {
m_childrenChangeEventFilter = new Internal::ChildrenChangeEventFilter(this);
connect(m_childrenChangeEventFilter.data(), SIGNAL(childrenChanged(QObject*)), this, SLOT(emitUpdateItem(QObject*)));
connect(m_childrenChangeEventFilter.data(), SIGNAL(childrenChanged(QObject*)), this, SLOT(emitParentChanged(QObject*)));
}
return m_childrenChangeEventFilter.data();
@@ -526,39 +498,31 @@ void NodeInstanceView::removeInstanceNodeRelationship(const ModelNode &node)
instance.makeInvalid();
}
void NodeInstanceView::emitOtherPropertyChanged()
void NodeInstanceView::notifyPropertyChange(const ModelNode &node, const QString &propertyName)
{
if (m_blockChangeSignal)
return;
if (hasInstanceForObject(sender()))
emit otherPropertyChanged(instanceForObject(sender()));
if (qmlModelView()) {
qmlModelView()->nodeInstancePropertyChanged(ModelNode(node,qmlModelView()), propertyName);
}
}
void NodeInstanceView::emitParentPropertyChanged()
void NodeInstanceView::setQmlModelView(QmlModelView *qmlModelView)
{
if (m_blockChangeSignal)
return;
if (hasInstanceForObject(sender()))
emit parentPropertyChanged(instanceForObject(sender()));
m_qmlModelView = qmlModelView;
}
void NodeInstanceView::emitTransformPropertyChanged()
QmlModelView *NodeInstanceView::qmlModelView() const
{
if (m_blockChangeSignal)
return;
if (hasInstanceForObject(sender()))
emit transformPropertyChanged(instanceForObject(sender()));
return m_qmlModelView.data();
}
void NodeInstanceView::emitUpdateItem(QObject *object)
void NodeInstanceView::emitParentChanged(QObject *child)
{
if (m_blockChangeSignal)
return;
if (hasInstanceForObject(object))
emit updateItem(instanceForObject(object));
if (hasInstanceForObject(child)) {
notifyPropertyChange(instanceForObject(child).modelNode(), "parent");
}
}
NodeInstance NodeInstanceView::loadNode(const ModelNode &node, QObject *objectToBeWrapped)
{
Q_ASSERT(node.isValid());

View File

@@ -57,6 +57,7 @@
#include <QmlBinding>
#include <QmlMetaType>
#include <QmlEngine>
#include <QSharedPointer>
#include <private/qmlcontext_p.h>
#include <private/qmllistaccessor_p.h>
@@ -65,12 +66,14 @@
#include <private/qmlgraphicsrectangle_p.h> // to get QmlGraphicsPen
#include <private/qmetaobjectbuilder_p.h>
#include <private/qmlvmemetaobject_p.h>
#include <private/qobject_p.h>
namespace QmlDesigner {
namespace Internal {
ChildrenChangeEventFilter::ChildrenChangeEventFilter(QObject *parent)
: QObject(parent)
{
@@ -81,7 +84,11 @@ bool ChildrenChangeEventFilter::eventFilter(QObject *object, QEvent *event)
{
switch (event->type()) {
case QEvent::ChildAdded:
case QEvent::ChildRemoved: emit childrenChanged(object); break;
case QEvent::ChildRemoved:
{
QChildEvent *childEvent = static_cast<QChildEvent*>(event);
emit childrenChanged(childEvent->child()); break;
}
default: break;
}
@@ -93,6 +100,7 @@ ObjectNodeInstance::ObjectNodeInstance(QObject *object)
m_object(object),
m_metaObject(0)
{
}
ObjectNodeInstance::~ObjectNodeInstance()
@@ -158,11 +166,39 @@ NodeInstanceView *ObjectNodeInstance::nodeInstanceView() const
return m_nodeInstanceView.data();
}
void ObjectNodeInstance::setNodeInstance(NodeInstanceView *view)
void ObjectNodeInstance::setNodeInstanceView(NodeInstanceView *view)
{
Q_ASSERT(!m_nodeInstanceView.data());
m_nodeInstanceView = view;
}
static bool hasPropertiesWitoutNotifications(const QMetaObject *metaObject)
{
for(int propertyIndex = QObject::staticMetaObject.propertyCount(); propertyIndex < metaObject->propertyCount(); propertyIndex++) {
if (!metaObject->property(propertyIndex).hasNotifySignal())
return true;
}
return false;
}
void ObjectNodeInstance::initializePropertyWatcher(const ObjectNodeInstance::Pointer &objectNodeInstance)
{
m_metaObject = new NodeInstanceMetaObject(objectNodeInstance);
const QMetaObject *metaObject = objectNodeInstance->object()->metaObject();
for(int propertyIndex = QObject::staticMetaObject.propertyCount(); propertyIndex < metaObject->propertyCount(); propertyIndex++) {
if (QmlMetaType::isQObject(metaObject->property(propertyIndex).userType())) {
QObject *propertyObject = QmlMetaType::toQObject(metaObject->property(propertyIndex).read(objectNodeInstance->object()));
if (propertyObject && hasPropertiesWitoutNotifications(propertyObject->metaObject())) {
new NodeInstanceMetaObject(objectNodeInstance, propertyObject, metaObject->property(propertyIndex).name());
}
}
}
m_signalSpy.setObjectNodeInstance(objectNodeInstance);
}
void ObjectNodeInstance::setId(const QString &id)
{
if (!m_id.isEmpty()) {
@@ -701,13 +737,6 @@ static bool metaObjectHasNotPropertyName(NodeInstanceMetaObject *metaObject, con
void ObjectNodeInstance::createDynamicProperty(const QString &name, const QString &/*typeName*/)
{
if (m_metaObject == 0) {
if (modelNode().isRootNode())
m_metaObject = new NodeInstanceMetaObject(object(), context());
else
m_metaObject = new NodeInstanceMetaObject(object(), 0);
}
if (metaObjectHasNotPropertyName(m_metaObject, name))
m_metaObject->createNewProperty(name);
}

View File

@@ -39,12 +39,15 @@
#include <propertymetainfo.h>
#include <nodeinstanceview.h>
#include "nodeinstancemetaobject.h"
#include "nodeinstancesignalspy.h"
QT_BEGIN_NAMESPACE
class QGraphicsItem;
class QmlContext;
class QmlMetaProperty;
class QmlContext;
class QmlBinding;
QT_END_NAMESPACE
namespace QmlDesigner {
@@ -91,8 +94,8 @@ public:
void setModelNode(const ModelNode &node);
NodeInstanceView *nodeInstanceView() const;
void setNodeInstance(NodeInstanceView *view);
void setNodeInstanceView(NodeInstanceView *view);
void initializePropertyWatcher(const Pointer &objectNodeInstance);
virtual void paint(QPainter *painter) const;
virtual bool isTopLevel() const;
@@ -186,6 +189,8 @@ private:
bool m_deleteHeldInstance;
QWeakPointer<QObject> m_object;
NodeInstanceMetaObject *m_metaObject;
NodeInstanceSignalSpy m_signalSpy;
};

View File

@@ -32,7 +32,9 @@
#include "objectnodeinstance.h"
QT_BEGIN_NAMESPACE
class QmlTransition;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -40,6 +40,7 @@
enum { debug = false };
QT_BEGIN_NAMESPACE
// Allow usage of QFileInfo in hash / qSort
@@ -53,6 +54,7 @@ static uint qHash(const QFileInfo &fileInfo)
return qHash(fileInfo.filePath());
}
QT_END_NAMESPACE
namespace QmlDesigner {

View File

@@ -33,7 +33,9 @@
#include <QObject>
#include <QList>
QT_BEGIN_NAMESPACE
class QTimer;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -42,11 +42,9 @@ namespace QmlDesigner {
QmlModelView::QmlModelView(QObject *parent)
: ForwardView<NodeInstanceView>(parent)
{
appendView(new NodeInstanceView(this));
connect(nodeInstanceView(), SIGNAL(transformPropertyChanged(NodeInstance)), SLOT(notifyTransformChanged(NodeInstance)));
connect(nodeInstanceView(), SIGNAL(parentPropertyChanged(NodeInstance)), SLOT(notifyParentChanged(NodeInstance)));
connect(nodeInstanceView(), SIGNAL(otherPropertyChanged(NodeInstance)), SLOT(notifyOtherPropertyChanged(NodeInstance)));
connect(nodeInstanceView(), SIGNAL(updateItem(NodeInstance)), SLOT(notifyUpdateItem(NodeInstance)));
NodeInstanceView *nodeInstanceView = new NodeInstanceView(this);
nodeInstanceView->setQmlModelView(this);
appendView(nodeInstanceView);
}
void QmlModelView::setCurrentState(const QmlModelState &state)
@@ -220,27 +218,6 @@ QmlObjectNode QmlModelView::fxObjectNodeForId(const QString &id)
return QmlObjectNode(modelNodeForId(id));
}
void QmlModelView::notifyTransformChanged(const NodeInstance &nodeInstance)
{
transformChanged(QmlObjectNode(ModelNode(nodeInstance.modelNode(), this)));
}
void QmlModelView::notifyParentChanged(const NodeInstance &nodeInstance)
{
parentChanged(QmlObjectNode(ModelNode(nodeInstance.modelNode(), this)));
}
void QmlModelView::notifyOtherPropertyChanged(const NodeInstance &nodeInstance)
{
otherPropertyChanged(QmlObjectNode(ModelNode(nodeInstance.modelNode(), this)));
}
void QmlModelView::notifyUpdateItem(const NodeInstance &nodeInstance)
{
updateItem(QmlObjectNode(ModelNode(nodeInstance.modelNode(), this)));
}
void QmlModelView::customNotification(const AbstractView * /* view */, const QString &identifier, const QList<ModelNode> &nodeList, const QList<QVariant> & /* data */)
{
if (identifier == "__state changed__") {
@@ -281,7 +258,36 @@ void QmlModelView::modelAboutToBeDetached(Model *model)
m_state = QmlModelState();
}
void QmlModelView::transformChanged(const QmlObjectNode &/*qmlObjectNode*/)
static bool isTransformProperty(const QString &name)
{
static QStringList transformProperties(QStringList() << "x"
<< "y"
<< "width"
<< "height"
<< "z"
<< "rotation"
<< "scale"
<< "transformOrigin");
return transformProperties.contains(name);
}
void QmlModelView::nodeInstancePropertyChanged(const ModelNode &node, const QString &propertyName)
{
QmlObjectNode qmlObjectNode(node);
if (!qmlObjectNode.isValid())
return;
if (isTransformProperty(propertyName))
transformChanged(qmlObjectNode, propertyName);
else if (propertyName == "parent")
parentChanged(qmlObjectNode);
else
otherPropertyChanged(qmlObjectNode, propertyName);
}
void QmlModelView::transformChanged(const QmlObjectNode &/*qmlObjectNode*/, const QString &/*propertyName*/)
{
}
@@ -290,15 +296,11 @@ void QmlModelView::parentChanged(const QmlObjectNode &/*qmlObjectNode*/)
}
void QmlModelView::otherPropertyChanged(const QmlObjectNode &/*qmlObjectNode*/)
void QmlModelView::otherPropertyChanged(const QmlObjectNode &/*qmlObjectNode*/, const QString &/*propertyName*/)
{
}
void QmlModelView::updateItem(const QmlObjectNode &/*qmlObjectNode*/)
{
}
void QmlModelView::stateChanged(const QmlModelState &newQmlModelState, const QmlModelState &oldQmlModelState)
{

View File

@@ -34,7 +34,9 @@
#include <QString>
#include <QStringList>
QT_BEGIN_NAMESPACE
class QmlValueType;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -36,7 +36,9 @@
#include <QWeakPointer>
QT_BEGIN_NAMESPACE
class QAction;
QT_END_NAMESPACE
namespace QmlDesigner {
namespace Internal {

View File

@@ -52,10 +52,12 @@
#include <QtGui/QComboBox>
#include <QtGui/QLabel>
QT_BEGIN_NAMESPACE
class QStackedWidget;
class QTabWidget;
class QVBoxLayout;
class QToolButton;
QT_END_NAMESPACE
namespace Core {
class SideBar;

View File

@@ -35,6 +35,8 @@
#include <QtCore/QPointer>
#include <QtCore/QTimer>
QT_BEGIN_NAMESPACE
class QStringList;
namespace ProjectExplorer {

View File

@@ -564,7 +564,7 @@ QmlJSTextEditor::QmlJSTextEditor(QWidget *parent) :
m_methodCombo(0),
m_modelManager(0)
{
qRegisterMetaType<SemanticInfo>("SemanticInfo");
qRegisterMetaType<QmlJSEditor::Internal::SemanticInfo>("QmlJSEditor::Internal::SemanticInfo");
m_semanticHighlighter = new SemanticHighlighter(this);
m_semanticHighlighter->start();
@@ -596,8 +596,8 @@ QmlJSTextEditor::QmlJSTextEditor(QWidget *parent) :
this, SLOT(onDocumentUpdated(QmlJS::Document::Ptr)));
}
connect(m_semanticHighlighter, SIGNAL(changed(SemanticInfo)),
this, SLOT(updateSemanticInfo(SemanticInfo)));
connect(m_semanticHighlighter, SIGNAL(changed(QmlJSEditor::Internal::SemanticInfo)),
this, SLOT(updateSemanticInfo(QmlJSEditor::Internal::SemanticInfo)));
}
QmlJSTextEditor::~QmlJSTextEditor()

View File

@@ -175,7 +175,7 @@ public:
void rehighlight(const Source &source);
Q_SIGNALS:
void changed(const SemanticInfo &semanticInfo);
void changed(const QmlJSEditor::Internal::SemanticInfo &semanticInfo);
protected:
virtual void run();
@@ -228,7 +228,7 @@ private slots:
void renameIdUnderCursor();
void semanticRehighlight();
void updateSemanticInfo(const SemanticInfo &semanticInfo);
void updateSemanticInfo(const QmlJSEditor::Internal::SemanticInfo &semanticInfo);
protected:
void contextMenuEvent(QContextMenuEvent *e);

View File

@@ -194,8 +194,15 @@ ImageFileFilterItem::ImageFileFilterItem(QObject *parent)
setFilter(filter);
}
CssFileFilterItem::CssFileFilterItem(QObject *parent)
: FileFilterBaseItem(parent)
{
setFilter(QLatin1String("*.css"));
}
} // namespace QmlProjectManager
QML_DEFINE_TYPE(QmlProject,1,0,QmlFiles,QmlProjectManager::QmlFileFilterItem)
QML_DEFINE_TYPE(QmlProject,1,0,JavaScriptFiles,QmlProjectManager::JsFileFilterItem)
QML_DEFINE_TYPE(QmlProject,1,0,ImageFiles,QmlProjectManager::ImageFileFilterItem)
QML_DEFINE_TYPE(QmlProject,1,0,CssFiles,QmlProjectManager::CssFileFilterItem)

View File

@@ -92,10 +92,19 @@ public:
ImageFileFilterItem(QObject *parent = 0);
};
class CssFileFilterItem : public FileFilterBaseItem {
Q_OBJECT
Q_PROPERTY(QString filter READ filter WRITE setFilter NOTIFY filterChanged())
public:
CssFileFilterItem(QObject *parent = 0);
};
} // namespace QmlProjectManager
QML_DECLARE_TYPE(QmlProjectManager::QmlFileFilterItem)
QML_DECLARE_TYPE(QmlProjectManager::JsFileFilterItem)
QML_DECLARE_TYPE(QmlProjectManager::ImageFileFilterItem)
QML_DECLARE_TYPE(QmlProjectManager::CssFileFilterItem)
#endif // FILEFILTERITEMS_HPROJECTITEM_H