forked from qt-creator/qt-creator
QmlDesigner: Add support for Component type
Component type is added to Component Library and can be dragged to the scene. Items under the component are not shown in the scene. Fixes: QDS-5093 Change-Id: I0c80647e73124866a8b772022a761ca6cbb545a1 Reviewed-by: Thomas Hartmann <thomas.hartmann@qt.io>
This commit is contained in:
@@ -617,7 +617,6 @@ class UnsupportedTypesByQmlUi : public QStringList
|
||||
{
|
||||
public:
|
||||
UnsupportedTypesByQmlUi() : QStringList({"ShaderEffect",
|
||||
"Component",
|
||||
"Drawer"})
|
||||
{
|
||||
append(UnsupportedTypesByVisualDesigner());
|
||||
|
@@ -99,8 +99,7 @@ FormEditorItem::FormEditorItem(const QmlItemNode &qmlItemNode, FormEditorScene*
|
||||
m_borderWidth(1.0),
|
||||
m_highlightBoundingRect(false),
|
||||
m_blurContent(false),
|
||||
m_isContentVisible(true),
|
||||
m_isFormEditorVisible(true)
|
||||
m_isContentVisible(true)
|
||||
{
|
||||
setCacheMode(QGraphicsItem::NoCache);
|
||||
setup();
|
||||
@@ -208,17 +207,6 @@ bool FormEditorItem::isContentVisible() const
|
||||
return m_isContentVisible;
|
||||
}
|
||||
|
||||
|
||||
bool FormEditorItem::isFormEditorVisible() const
|
||||
{
|
||||
return m_isFormEditorVisible;
|
||||
}
|
||||
void FormEditorItem::setFormEditorVisible(bool isVisible)
|
||||
{
|
||||
m_isFormEditorVisible = isVisible;
|
||||
setVisible(isVisible);
|
||||
}
|
||||
|
||||
QPointF FormEditorItem::center() const
|
||||
{
|
||||
return mapToScene(qmlItemNode().instanceBoundingRect().center());
|
||||
|
@@ -104,9 +104,6 @@ public:
|
||||
void setContentVisible(bool visible);
|
||||
bool isContentVisible() const;
|
||||
|
||||
bool isFormEditorVisible() const;
|
||||
void setFormEditorVisible(bool isVisible);
|
||||
|
||||
QPointF center() const;
|
||||
qreal selectionWeigth(const QPointF &point, int iteration);
|
||||
|
||||
@@ -152,7 +149,6 @@ private: // variables
|
||||
bool m_highlightBoundingRect;
|
||||
bool m_blurContent;
|
||||
bool m_isContentVisible;
|
||||
bool m_isFormEditorVisible;
|
||||
};
|
||||
|
||||
class FormEditorFlowItem : public FormEditorItem
|
||||
|
@@ -199,16 +199,6 @@ void FormEditorView::removeNodeFromScene(const QmlItemNode &qmlItemNode)
|
||||
m_currentTool->itemsAboutToRemoved(removedItemList);
|
||||
}
|
||||
|
||||
void FormEditorView::hideNodeFromScene(const QmlItemNode &qmlItemNode)
|
||||
{
|
||||
if (FormEditorItem *item = m_scene->itemForQmlItemNode(qmlItemNode)) {
|
||||
QList<FormEditorItem*> removedItems = scene()->itemsForQmlItemNodes(qmlItemNode.allSubModelNodes());
|
||||
removedItems.append(item);
|
||||
m_currentTool->itemsAboutToRemoved(removedItems);
|
||||
item->setFormEditorVisible(false);
|
||||
}
|
||||
}
|
||||
|
||||
void FormEditorView::createFormEditorWidget()
|
||||
{
|
||||
m_formEditorWidget = QPointer<FormEditorWidget>(new FormEditorWidget(this));
|
||||
@@ -248,10 +238,7 @@ void FormEditorView::temporaryBlockView(int duration)
|
||||
|
||||
void FormEditorView::nodeCreated(const ModelNode &node)
|
||||
{
|
||||
//If the node has source for components/custom parsers we ignore it.
|
||||
if (QmlItemNode::isValidQmlItemNode(node) && node.nodeSourceType() == ModelNode::NodeWithoutSource) //only setup QmlItems
|
||||
setupFormEditorItemTree(QmlItemNode(node));
|
||||
else if (QmlVisualNode::isFlowTransition(node))
|
||||
if (QmlVisualNode::isFlowTransition(node))
|
||||
setupFormEditorItemTree(QmlItemNode(node));
|
||||
}
|
||||
|
||||
@@ -349,8 +336,26 @@ static inline bool hasNodeSourceParent(const ModelNode &node)
|
||||
|
||||
void FormEditorView::nodeReparented(const ModelNode &node, const NodeAbstractProperty &/*newPropertyParent*/, const NodeAbstractProperty &/*oldPropertyParent*/, AbstractView::PropertyChangeFlags /*propertyChange*/)
|
||||
{
|
||||
if (hasNodeSourceParent(node))
|
||||
hideNodeFromScene(node);
|
||||
// If node is not connected to scene root, don't do anything yet to avoid duplicated effort,
|
||||
// as any removal or addition will remove or add descendants as well.
|
||||
if (!node.isInHierarchy())
|
||||
return;
|
||||
|
||||
QmlItemNode itemNode(node);
|
||||
if (hasNodeSourceParent(node)) {
|
||||
if (FormEditorItem *item = m_scene->itemForQmlItemNode(itemNode)) {
|
||||
QList<FormEditorItem *> removed = scene()->itemsForQmlItemNodes(itemNode.allSubModelNodes());
|
||||
removed.append(item);
|
||||
m_currentTool->itemsAboutToRemoved(removed);
|
||||
removeNodeFromScene(itemNode);
|
||||
}
|
||||
} else if (itemNode.isValid() && node.nodeSourceType() == ModelNode::NodeWithoutSource) {
|
||||
if (!m_scene->itemForQmlItemNode(itemNode)) {
|
||||
setupFormEditorItemTree(itemNode);
|
||||
// Simulate selection change to refresh tools
|
||||
selectedNodesChanged(selectedModelNodes(), {});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
WidgetInfo FormEditorView::widgetInfo()
|
||||
@@ -603,8 +608,7 @@ void FormEditorView::auxiliaryDataChanged(const ModelNode &node, const PropertyN
|
||||
if (name == "invisible") {
|
||||
if (FormEditorItem *item = scene()->itemForQmlItemNode(QmlItemNode(node))) {
|
||||
bool isInvisible = data.toBool();
|
||||
if (item->isFormEditorVisible())
|
||||
item->setVisible(!isInvisible);
|
||||
item->setVisible(!isInvisible);
|
||||
ModelNode newNode(node);
|
||||
if (isInvisible)
|
||||
newNode.deselectNode();
|
||||
|
@@ -144,7 +144,6 @@ protected:
|
||||
private:
|
||||
void setupFormEditorItemTree(const QmlItemNode &qmlItemNode);
|
||||
void removeNodeFromScene(const QmlItemNode &qmlItemNode);
|
||||
void hideNodeFromScene(const QmlItemNode &qmlItemNode);
|
||||
void createFormEditorWidget();
|
||||
void temporaryBlockView(int duration = 1000);
|
||||
void resetNodeInstanceView();
|
||||
|
@@ -34,6 +34,8 @@
|
||||
|
||||
#include <nodemetainfo.h>
|
||||
|
||||
#include <utils/algorithm.h>
|
||||
|
||||
#include <QGraphicsSceneMouseEvent>
|
||||
#include <QDebug>
|
||||
|
||||
@@ -242,9 +244,23 @@ void SelectionTool::dragMoveEvent(const QList<QGraphicsItem*> &/*itemList*/, QGr
|
||||
{
|
||||
}
|
||||
|
||||
void SelectionTool::itemsAboutToRemoved(const QList<FormEditorItem*> &/*itemList*/)
|
||||
void SelectionTool::itemsAboutToRemoved(const QList<FormEditorItem*> &itemList)
|
||||
{
|
||||
const QList<FormEditorItem *> current = items();
|
||||
|
||||
QList<FormEditorItem *> remaining = Utils::filtered(current, [&itemList](const FormEditorItem *item) {
|
||||
return !itemList.contains(item);
|
||||
});
|
||||
|
||||
if (!remaining.isEmpty()) {
|
||||
m_selectionIndicator.setItems(remaining);
|
||||
m_resizeIndicator.setItems(remaining);
|
||||
m_rotationIndicator.setItems(remaining);
|
||||
m_anchorIndicator.setItems(remaining);
|
||||
m_bindingIndicator.setItems(remaining);
|
||||
} else {
|
||||
clear();
|
||||
}
|
||||
}
|
||||
|
||||
void SelectionTool::clear()
|
||||
|
@@ -1085,10 +1085,18 @@ void NavigatorTreeModel::moveNodesInteractive(NodeAbstractProperty &parentProper
|
||||
if (modelNode.isValid()
|
||||
&& modelNode != parentProperty.parentModelNode()
|
||||
&& !modelNode.isAncestorOf(parentProperty.parentModelNode())
|
||||
&& (modelNode.metaInfo().isSubclassOf(propertyQmlType) || propertyQmlType == "alias")) {
|
||||
&& (modelNode.metaInfo().isSubclassOf(propertyQmlType)
|
||||
|| propertyQmlType == "alias"
|
||||
|| parentProperty.name() == "data")) {
|
||||
//### todo: allowing alias is just a heuristic
|
||||
//once the MetaInfo is part of instances we can do this right
|
||||
|
||||
// We assume above that "data" property in parent accepts all types.
|
||||
// This is a workaround for Component parents to accept children, even though they
|
||||
// do not have an actual "data" property or apparently any other default property.
|
||||
// When the actual reparenting happens, model will create the "data" property if
|
||||
// it is missing.
|
||||
|
||||
bool nodeCanBeMovedToParentProperty = removeModelNodeFromNodeProperty(parentProperty, modelNode);
|
||||
if (nodeCanBeMovedToParentProperty) {
|
||||
reparentModelNodeToNodeProperty(parentProperty, modelNode);
|
||||
|
@@ -309,7 +309,11 @@ QmlObjectNode QmlVisualNode::createQmlObjectNode(AbstractView *view,
|
||||
}
|
||||
}
|
||||
|
||||
newQmlObjectNode = QmlObjectNode(view->createModelNode(itemLibraryEntry.typeName(), majorVersion, minorVersion, propertyPairList));
|
||||
ModelNode::NodeSourceType nodeSourceType = ModelNode::NodeWithoutSource;
|
||||
if (itemLibraryEntry.typeName() == "QtQml.Component")
|
||||
nodeSourceType = ModelNode::NodeWithComponentSource;
|
||||
|
||||
newQmlObjectNode = QmlObjectNode(view->createModelNode(itemLibraryEntry.typeName(), majorVersion, minorVersion, propertyPairList, {}, {}, nodeSourceType));
|
||||
} else {
|
||||
newQmlObjectNode = createQmlObjectNodeFromSource(view, itemLibraryEntry.qmlSource(), position);
|
||||
}
|
||||
|
@@ -432,4 +432,20 @@ MetaInfo {
|
||||
}
|
||||
}
|
||||
|
||||
Type {
|
||||
name: "QtQml.Component"
|
||||
icon: ":/qtquickplugin/images/item-icon16.png"
|
||||
|
||||
Hints {
|
||||
canBeDroppedInNavigator: true
|
||||
canBeDroppedInFormEditor: false
|
||||
}
|
||||
|
||||
ItemLibraryEntry {
|
||||
name: "Component"
|
||||
category: "e.Qt Quick - Component"
|
||||
libraryIcon: ":/qtquickplugin/images/item-icon.png"
|
||||
version: "2.0"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user