Commit f950b8d7 authored by Thomas Hartmann's avatar Thomas Hartmann Committed by Marco Bubke

QmlDesigner: reactivating subcomponent editing

This includes refactoring the DesignDocumentController.
In the ComponentTextMoifier I use replaced because it is not blocked by
beginEditBlock() of the text cursor.

I use the same pattern now for ComponentView like for all the other
views.
The view is created and controlled by DesignModeWidget because we
have only a single instance.

Change-Id: I7809b96f52f4d275f0231f3961c3c4bc2618ce89
Reviewed-on: http://codereview.qt.nokia.com/96Reviewed-by: default avatarMarco Bubke <marco.bubke@nokia.com>
parent e3842f99
......@@ -39,30 +39,17 @@
namespace QmlDesigner {
ComponentAction::ComponentAction(QObject *parent)
: QWidgetAction(parent),
m_componentView(new ComponentView(this))
ComponentAction::ComponentAction(ComponentView *componentView)
: QWidgetAction(componentView),
m_componentView(componentView)
{
}
void ComponentAction::setModel(Model* model)
{
if (model == m_componentView->model())
return;
blockSignals(true);
if (model)
model->attachView(m_componentView.data());
else if (m_componentView->model())
m_componentView->model()->detachView(m_componentView.data());
blockSignals(false);
}
QWidget *ComponentAction::createWidget(QWidget *parent)
{
QComboBox *comboBox = new QComboBox(parent);
comboBox->setMinimumWidth(120);
comboBox->setToolTip(tr("Edit sub components defined in this file"));
comboBox->setModel(m_componentView->standardItemModel());
connect(comboBox, SIGNAL(currentIndexChanged(int)), SLOT(emitCurrentComponentChanged(int)));
......
......@@ -50,8 +50,7 @@ class ComponentAction : public QWidgetAction
{
Q_OBJECT
public:
ComponentAction(QObject *parent);
void setModel(Model* model);
ComponentAction(ComponentView *componentView);
protected:
QWidget *createWidget(QWidget *parent);
......
......@@ -31,9 +31,11 @@
**************************************************************************/
#include "componentview.h"
#include "componentaction.h"
#include <QtDebug>
#include <nodemetainfo.h>
#include <nodeabstractproperty.h>
#include <QStandardItemModel>
// silence gcc warnings about unused parameters
......@@ -43,7 +45,8 @@ namespace QmlDesigner {
ComponentView::ComponentView(QObject *parent)
: AbstractView(parent),
m_standardItemModel(new QStandardItemModel(this)),
m_listChanged(false)
m_listChanged(false),
m_componentAction(new ComponentAction(this))
{
}
......@@ -56,6 +59,7 @@ void ComponentView::nodeAboutToBeRemoved(const ModelNode &removedNode)
if (item->data(ModelNodeRole).value<ModelNode>() == removedNode)
m_standardItemModel->removeRow(index);
}
searchForComponentAndRemoveFromList(removedNode);
}
QStandardItemModel *ComponentView::standardItemModel() const
......@@ -86,17 +90,29 @@ void ComponentView::modelAttached(Model *model)
if (AbstractView::model() == model)
return;
bool block = m_componentAction->blockSignals(true);
m_standardItemModel->clear();
AbstractView::modelAttached(model);
Q_ASSERT(model->masterModel());
appendWholeDocumentAsComponent();
searchForComponentAndAddToList(rootModelNode());
m_componentAction->blockSignals(block);
}
void ComponentView::modelAboutToBeDetached(Model *model)
{
bool block = m_componentAction->blockSignals(true);
m_standardItemModel->clear();
AbstractView::modelAboutToBeDetached(model);
m_componentAction->blockSignals(block);
}
ComponentAction *ComponentView::action()
{
return m_componentAction;
}
void ComponentView::nodeCreated(const ModelNode &createdNode)
......@@ -112,48 +128,59 @@ void ComponentView::searchForComponentAndAddToList(const ModelNode &node)
foreach (const ModelNode &childNode, nodeList) {
if (childNode.type() == "Qt/Component") {
if (childNode.type() == "QtQuick.Component") {
if (!childNode.id().isEmpty()) {
QStandardItem *item = new QStandardItem(childNode.id());
item->setData(QVariant::fromValue(childNode), ModelNodeRole);
item->setEditable(false);
m_standardItemModel->appendRow(item);
} else {
QString description;
if (!childNode.parentProperty().parentModelNode().id().isEmpty())
description = childNode.parentProperty().parentModelNode().id() + QLatin1Char(' ');
else
description = childNode.parentProperty().parentModelNode().simplifiedTypeName() + QLatin1Char(' ');
description += childNode.parentProperty().name();
QStandardItem *item = new QStandardItem(description);
item->setData(QVariant::fromValue(childNode), ModelNodeRole);
item->setEditable(false);
m_standardItemModel->appendRow(item);
}
} else if (node.metaInfo().isValid() && node.metaInfo().isComponent() && !m_componentList.contains(node.type())) {
m_componentList.append(node.type());
m_componentList.sort();
m_listChanged = true;
}
}
}
}
void ComponentView::nodeRemoved(const ModelNode & /*removedNode*/, const NodeAbstractProperty & /*parentProperty*/, PropertyChangeFlags /*propertyChange*/)
void ComponentView::nodeRemoved(const ModelNode & /* removedNode */, const NodeAbstractProperty & /*parentProperty*/, PropertyChangeFlags /*propertyChange*/)
{
}
void ComponentView::searchForComponentAndRemoveFromList(const ModelNode &node)
{
QList<ModelNode> nodeList;
nodeList.append(node);
nodeList.append(node.allSubModelNodes());
foreach (const ModelNode &childNode, nodeList) {
if (childNode.type() == "QtQuick.Component") {
if (!childNode.id().isEmpty()) {
for (int row = 0; row < m_standardItemModel->rowCount(); row++) {
if (m_standardItemModel->item(row)->text() == childNode.id())
m_standardItemModel->removeRow(row);
}
}
} else if (node.metaInfo().isComponent() && !m_componentList.contains(childNode.type())) {
m_componentList.append(childNode.type());
m_componentList.sort();
m_listChanged = true;
}
}
}
//void ComponentView::searchForComponentAndRemoveFromList(const ModelNode &node)
//{
// QList<ModelNode> nodeList;
// nodeList.append(node);
// nodeList.append(node.allSubModelNodes());
//
//
// foreach (const ModelNode &childNode, nodeList) {
// if (node.type() == "Qt/Component") {
// if (!node.id().isEmpty()) {
// for(int row = 0; row < m_standardItemModel->rowCount(); row++) {
// if (m_standardItemModel->item(row)->text() == node.id())
// m_standardItemModel->removeRow(row);
// }
// }
// } else if (node.metaInfo().isComponent() && !m_componentList.contains(node.type())) {
// m_componentList.append(node.type());
// m_componentList.sort();
// m_listChanged = true;
// }
// }
//}
void ComponentView::nodeAboutToBeReparented(const ModelNode &/*node*/, const NodeAbstractProperty &/*newPropertyParent*/, const NodeAbstractProperty &/*oldPropertyParent*/, AbstractView::PropertyChangeFlags /*propertyChange*/) {}
void ComponentView::nodeReparented(const ModelNode &/*node*/, const NodeAbstractProperty &/*newPropertyParent*/, const NodeAbstractProperty &/*oldPropertyParent*/, AbstractView::PropertyChangeFlags /*propertyChange*/) {}
void ComponentView::nodeIdChanged(const ModelNode& /*node*/, const QString& /*newId*/, const QString& /*oldId*/) {}
......
......@@ -44,6 +44,8 @@ QT_END_NAMESPACE
namespace QmlDesigner {
class ComponentAction;
class ComponentView : public AbstractView
{
Q_OBJECT
......@@ -59,6 +61,8 @@ public:
void modelAttached(Model *model);
void modelAboutToBeDetached(Model *model);
ComponentAction *action();
void nodeCreated(const ModelNode &createdNode);
void nodeAboutToBeRemoved(const ModelNode &removedNode);
void nodeRemoved(const ModelNode &removedNode, const NodeAbstractProperty &parentProperty, PropertyChangeFlags propertyChange);
......@@ -107,13 +111,14 @@ signals:
private: //functions
void updateModel();
void searchForComponentAndAddToList(const ModelNode &node);
// void searchForComponentAndRemoveFromList(const ModelNode &node);
void searchForComponentAndRemoveFromList(const ModelNode &node);
void appendWholeDocumentAsComponent();
private:
QStringList m_componentList;
QStandardItemModel *m_standardItemModel;
bool m_listChanged;
ComponentAction *m_componentAction;
};
} // namespace QmlDesigner
......
......@@ -48,12 +48,12 @@
#include <componenttextmodifier.h>
#include <metainfo.h>
#include <invalidargumentexception.h>
#include <componentview.h>
#include <componentaction.h>
#include <qmlobjectnode.h>
#include <rewriterview.h>
#include <rewritingexception.h>
#include <nodelistproperty.h>
#include <toolbox.h>
#include <variantproperty.h>
#include <rewritingexception.h>
......@@ -97,6 +97,7 @@ public:
QWeakPointer<StatesEditorView> statesEditorView;
QWeakPointer<QStackedWidget> stackedWidget;
QWeakPointer<NodeInstanceView> nodeInstanceView;
QWeakPointer<ComponentView> componentView;
QWeakPointer<QmlDesigner::Model> model;
QWeakPointer<QmlDesigner::Model> subComponentModel;
......@@ -112,7 +113,6 @@ public:
QUrl searchPath;
bool documentLoaded;
bool syncBlocked;
QWeakPointer<ComponentAction> componentAction;
};
......@@ -256,6 +256,12 @@ void DesignDocumentController::setNodeInstanceView(NodeInstanceView *nodeInstanc
m_d->nodeInstanceView = nodeInstanceView;
}
void DesignDocumentController::setComponentView(ComponentView *componentView)
{
m_d->componentView = componentView;
connect(m_d->componentView->action(), SIGNAL(currentComponentChanged(ModelNode)), SLOT(changeCurrentModelTo(ModelNode)));
}
QString DesignDocumentController::displayName() const
{
if (fileName().isEmpty())
......@@ -331,6 +337,8 @@ QList<RewriterView::Error> DesignDocumentController::loadMaster(QPlainTextEdit *
loadCurrentModel();
m_d->masterModel->attachView(m_d->componentView.data());
return m_d->rewriterView->errors();
}
......@@ -340,6 +348,17 @@ void DesignDocumentController::changeCurrentModelTo(const ModelNode &componentNo
QWeakPointer<Model> oldModel = m_d->model;
Q_ASSERT(oldModel.data());
QString componentText = m_d->rewriterView->extractText(QList<ModelNode>() << componentNode).value(componentNode);
if (componentText.isEmpty())
return;
bool explicitComponent = false;
if (componentText.contains("Component")) { //explicit component
explicitComponent = true;
}
if (m_d->model == m_d->subComponentModel) {
//change back to master model
m_d->model->detachView(m_d->rewriterView.data());
......@@ -356,10 +375,20 @@ void DesignDocumentController::changeCurrentModelTo(const ModelNode &componentNo
if (m_d->componentTextModifier)
delete m_d->componentTextModifier;
int componentStartOffset = m_d->rewriterView->firstDefinitionInsideOffset(componentNode);
int componentEndOffset = componentStartOffset + m_d->rewriterView->firstDefinitionInsideLength(componentNode);
int componentStartOffset;
int componentEndOffset;
int rootStartOffset = m_d->rewriterView->nodeOffset(rootModelNode);
if (explicitComponent) { //the component is explciit we have to find the first definition inside
componentStartOffset = m_d->rewriterView->firstDefinitionInsideOffset(componentNode);
componentEndOffset = componentStartOffset + m_d->rewriterView->firstDefinitionInsideLength(componentNode);
} else { //the component is implicit
componentStartOffset = m_d->rewriterView->nodeOffset(componentNode);
componentEndOffset = componentStartOffset + m_d->rewriterView->nodeLength(componentNode);
}
m_d->componentTextModifier = new ComponentTextModifier (m_d->textModifier, componentStartOffset, componentEndOffset, rootStartOffset);
......@@ -392,21 +421,11 @@ void DesignDocumentController::loadCurrentModel()
m_d->model->attachView(m_d->navigator.data());
m_d->itemLibraryView->widget()->setResourcePath(QFileInfo(m_d->fileName).absolutePath());
if (!m_d->componentAction) {
m_d->componentAction = new ComponentAction(m_d->formEditorView->widget());
m_d->componentAction->setModel(m_d->model.data());
connect(m_d->componentAction.data(), SIGNAL(currentComponentChanged(ModelNode)), SLOT(changeCurrentModelTo(ModelNode)));
m_d->formEditorView->widget()->toolBox()->addAction(m_d->componentAction.data());
}
// Disable switching between in file components for the time being
m_d->componentAction->setVisible(false);
connect(m_d->itemLibraryView->widget(), SIGNAL(itemActivated(const QString&)), m_d->formEditorView.data(), SLOT(activateItemCreator(const QString&)));
m_d->model->attachView(m_d->formEditorView.data());
m_d->model->attachView(m_d->itemLibraryView.data());
if (!m_d->textEdit->parent()) // hack to prevent changing owner of external text edit
m_d->stackedWidget->addWidget(m_d->textEdit.data());
......
......@@ -56,6 +56,7 @@ class QmlObjectNode;
class RewriterView;
class ItemLibraryView;
class NavigatorView;
class ComponentView;
class PropertyEditor;
class StatesEditorView;
class FormEditorView;
......@@ -98,6 +99,7 @@ public:
void setStatesEditorView(StatesEditorView* statesEditorView);
void setFormEditorView(FormEditorView *formEditorView);
void setNodeInstanceView(NodeInstanceView *nodeInstanceView);
void setComponentView(ComponentView *componentView);
signals:
void displayNameChanged(const QString &newFileName);
......
......@@ -39,7 +39,7 @@ ComponentTextModifier::ComponentTextModifier(TextModifier *originalModifier, int
m_componentEndOffset(componentEndOffset),
m_rootStartOffset(rootStartOffset)
{
connect(m_originalModifier->textDocument(), SIGNAL(contentsChange(int,int,int)), this, SLOT(contentsChange(int,int,int)));
connect(m_originalModifier, SIGNAL(replaced(int, int, int)), this, SLOT(contentsChange(int,int,int)));
connect(m_originalModifier, SIGNAL(textChanged()), this, SIGNAL(textChanged()));
connect(m_originalModifier, SIGNAL(replaced(int, int, int)), this, SIGNAL(replaced(int, int, int)));
......
......@@ -40,7 +40,8 @@
#include <formeditorwidget.h>
#include <stateseditorwidget.h>
#include <itemlibrarywidget.h>
#include <componentaction.h>
#include <toolbox.h>
#include <coreplugin/coreconstants.h>
#include <coreplugin/modemanager.h>
......@@ -312,6 +313,7 @@ void DesignModeWidget::showEditor(Core::IEditor *editor)
newDocument->setStatesEditorView(m_statesEditorView.data());
newDocument->setItemLibraryView(m_itemLibraryView.data());
newDocument->setFormEditorView(m_formEditorView.data());
newDocument->setComponentView(m_componentView.data());
newDocument->setFileName(fileName);
......@@ -674,6 +676,8 @@ void DesignModeWidget::setup()
m_formEditorView = new FormEditorView(this);
m_componentView = new ComponentView(this);
m_formEditorView->widget()->toolBox()->addLeftSideAction(m_componentView->action());
m_fakeToolBar = Core::EditorManager::createToolBar(this);
m_mainSplitter = new MiniSplitter(this);
......
......@@ -45,6 +45,7 @@
#include <navigatorwidget.h>
#include <navigatorview.h>
#include <stateseditorview.h>
#include <componentview.h>
#include <modelnode.h>
#include <formeditorview.h>
#include <propertyeditor.h>
......@@ -185,6 +186,7 @@ private:
QWeakPointer<PropertyEditor> m_propertyEditorView;
QWeakPointer<StatesEditorView> m_statesEditorView;
QWeakPointer<FormEditorView> m_formEditorView;
QWeakPointer<ComponentView> m_componentView;
QWeakPointer<NodeInstanceView> m_nodeInstanceView;
bool m_syncWithTextEdit;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment