Commit 81008125 authored by Jochen Becher's avatar Jochen Becher

ModelEditor: Support custom relations in configuration files

Change-Id: I87338f290bd1ea729682236df8b017516a18e7bb
Reviewed-by: Tobias Hunger's avatarTobias Hunger <tobias.hunger@qt.io>
parent 42844215
...@@ -2,6 +2,9 @@ ...@@ -2,6 +2,9 @@
// //
// Language syntax and commands: // Language syntax and commands:
// //
//
// An Icon defines an icon of an element selected by stereotype.
//
// Icon { // Icon {
// id: <id> // id: <id>
// title: <a UI title. Defaults to the id of the icon.> // title: <a UI title. Defaults to the id of the icon.>
...@@ -29,6 +32,8 @@ ...@@ -29,6 +32,8 @@
// RoundedRect { x: <x>; y: <y>; width: <width>; height: <height>; radius: <radius> } // RoundedRect { x: <x>; y: <y>; width: <width>; height: <height>; radius: <radius> }
// Circle { x: <center_x>; y: <center_y>; radius: <radius> } // Circle { x: <center_x>; y: <center_y>; radius: <radius> }
// Ellipse { x: <center_x>; y: <center_y>; radiusX: <radius_x>; radiusY: <radius_y> } // Ellipse { x: <center_x>; y: <center_y>; radiusX: <radius_x>; radiusY: <radius_y> }
// Diamond { x: <center_x>; y: <center_y>; width: <width>; height: <height; filled: <yes or no or true or false> }
// Triangle { x: <center_x>; y: <center_y>; width: <width>; height: <height; filled: <yes or no or true or false> }
// Arc { x: <center_x>; y: <center_y>; radiusX: <radius_x>; radiusY: <radius_y>; start: <start_angle>; span: <span_angle> } // Arc { x: <center_x>; y: <center_y>; radiusX: <radius_x>; radiusY: <radius_y>; start: <start_angle>; span: <span_angle> }
// MoveTo { x: <x>; y: <y> } // MoveTo { x: <x>; y: <y> }
// LineTo { x: <x>; y: <y> } // LineTo { x: <x>; y: <y> }
...@@ -38,6 +43,79 @@ ...@@ -38,6 +43,79 @@
// } // }
// } // }
// //
//
// A Relation defines a new relation between to items:
//
// Relation {
// id: <id>
// title: <a UI title. Defaults to the id of the icon.>
// elements: <A list of elements that may be the start or end element of the relation. Can be one of
// class, component, package, diagram, item or any id of an Icon definition. Must be given.>
// stereotype: <Stereotype as a string. Defaults to nothing.>
// name: <Name of the relation. Defaults to nothing.>
// direction: <One of AtoB, BtoA or Bi. Defaults to nothing.>
// pattern: <The pattern used for the relation shaft.
// One of solid, dash, dot, dashdot, dashdotdot. Defaults to solid>
// color: <The color of the relation. One of A or B (uses the color of the respective end element) or
// any valid color (#rrggbb or a color name). Defaults to A.>
// End {
// end: <One of A or B. Defines the settings of the relations end.>
// elements: <Overrides the elements property of parent.>
// role: <The role of the end. A string that defaults to nothing.>
// cardinality: <An integer or a string defining the cardinality of the end. Defaults to nothing.>
// navigable: <If the end is navigable. One of Yes, No, True, False. Defaults to nothing.>
// Shape {
// }
// }
// }
//
//
// A Dependency defines a number of settings of a dependency specialization:
//
// Dependency {
// id: <id>
// title: <a UI title. Defaults to the id of the icon.>
// elements: <A list of elements that provides this specialization in its menu. Can be one of
// class, component, package, diagram, item or any id of an Icon definition. Must be given.>
// stereotype: <Stereotype as a string. Defaults to nothing.>
// name: <Name of the relation. Defaults to nothing.>
// direction: <One of AtoB, BtoA or Bi. Defaults to nothing.>
// }
//
//
// An Inheritance defines settings of an inheritance specialization:
//
// Inheritance {
// id: <id>
// title: <a UI title. Defaults to the id of the icon.>
// elements: <A list of elements that provides this specialization in its menu. Can be one of
// class or any id of an Icon definition for classes. Defaults to class.>
// stereotype: <Stereotype as a string. Defaults to nothing.>
// name: <Name of the relation. Defaults to nothing.>
// }
//
//
// An Association defines settings of an association specialization:
//
// Association {
// id: <id>
// title: <a UI title. Defaults to the id of the icon.>
// elements: <A list of elements that provides this specialization in its menu. Can be one of
// class or any id of an Icon definition for classes. Defaults to class.>
// stereotype: <Stereotype as a string. Defaults to nothing.>
// name: <Name of the relation. Defaults to nothing.>
// End {
// end: <One of A or B. Defines the settings of the relations end.>
// role: <The role of the end. A string that defaults to nothing.>
// cardinality: <An integer or a string defining the cardinality of the end. Defaults to nothing.>
// navigable: <If the end is navigable. One of Yes, No, True, False. Defaults to nothing.>
// relationship: <One of Association, Aggregation, Composition. Defaults to Association.>
// }
// }
//
//
// A toolbar of icons. If no toolbar is defined the standard toolbar is shown.
//
// Toolbar { // Toolbar {
// id: <id> // id: <id>
// title: <a Ui title. Defaults to the id of the toolbar> // title: <a Ui title. Defaults to the id of the toolbar>
...@@ -104,6 +182,54 @@ Icon { ...@@ -104,6 +182,54 @@ Icon {
} }
} }
Association {
id: AggregationOne
title: "Aggregation (?:1)"
End {
end: A
cardinality: 1
navigable: yes
relationship: aggregation
}
}
Association {
id: AggregationMany
title: "Aggregation (?:N)"
End {
end: A
cardinality: "*"
navigable: yes
relationship: aggregation
}
}
// ********************
// ** Class Toolbars **
// ********************
Toolbar {
id: ClassToolbar
element: class
Tools {
Tool { element: dependency }
Tool { element: inheritance }
Tool { element: association }
Tool { element: AggregationOne }
Tool { element: AggregationMany }
}
}
Toolbar {
id: InterfaceToolbar
element: Interface
Tools {
Tool { element: dependency }
Tool { element: inheritance }
}
}
// **************** // ****************
// ** Components ** // ** Components **
// **************** // ****************
...@@ -276,6 +402,34 @@ Icon { ...@@ -276,6 +402,34 @@ Icon {
} }
} }
Relation {
id: Controlflow
pattern: solid
color: A
End {
end: A
elements: Start, Activity, Condition, HorizontalBar, VerticalBar
role: ""
}
End {
end: B
elements: Activity, Condition, HorizontalBar, VerticalBar, Termination
head: filledtriangle
//Shape {
// Triangle { x: 6; y: 5.2; width: 12; height: 10.4; filled: yes }
//}
}
}
Toolbar {
id: ActivityToolbar
element: Start, Activity, Condition, HorizontalBar, VerticalBar
Tools {
Tool { element: Controlflow }
Tool { element: dependency }
}
}
// ************** // **************
// ** Toolbars ** // ** Toolbars **
// ************** // **************
......
...@@ -252,6 +252,8 @@ QtcLibrary { ...@@ -252,6 +252,8 @@ QtcLibrary {
"serializer/modelserializer.h", "serializer/modelserializer.h",
"serializer/projectserializer.cpp", "serializer/projectserializer.cpp",
"serializer/projectserializer.h", "serializer/projectserializer.h",
"stereotype/customrelation.cpp",
"stereotype/customrelation.h",
"stereotype/iconshape.cpp", "stereotype/iconshape.cpp",
"stereotype/iconshape.h", "stereotype/iconshape.h",
"stereotype/shape.h", "stereotype/shape.h",
......
...@@ -71,6 +71,8 @@ void ConfigController::readStereotypeDefinitions(const QString &path) ...@@ -71,6 +71,8 @@ void ConfigController::readStereotypeDefinitions(const QString &path)
StereotypeDefinitionParser parser; StereotypeDefinitionParser parser;
connect(&parser, &StereotypeDefinitionParser::iconParsed, connect(&parser, &StereotypeDefinitionParser::iconParsed,
this, &ConfigController::onStereotypeIconParsed); this, &ConfigController::onStereotypeIconParsed);
connect(&parser, &StereotypeDefinitionParser::relationParsed,
this, &ConfigController::onRelationParsed);
connect(&parser, &StereotypeDefinitionParser::toolbarParsed, connect(&parser, &StereotypeDefinitionParser::toolbarParsed,
this, &ConfigController::onToolbarParsed); this, &ConfigController::onToolbarParsed);
...@@ -116,6 +118,11 @@ void ConfigController::onStereotypeIconParsed(const StereotypeIcon &stereotypeIc ...@@ -116,6 +118,11 @@ void ConfigController::onStereotypeIconParsed(const StereotypeIcon &stereotypeIc
d->m_stereotypeController->addStereotypeIcon(stereotypeIcon); d->m_stereotypeController->addStereotypeIcon(stereotypeIcon);
} }
void ConfigController::onRelationParsed(const CustomRelation &customRelation)
{
d->m_stereotypeController->addCustomRelation(customRelation);
}
void ConfigController::onToolbarParsed(const Toolbar &toolbar) void ConfigController::onToolbarParsed(const Toolbar &toolbar)
{ {
d->m_stereotypeController->addToolbar(toolbar); d->m_stereotypeController->addToolbar(toolbar);
......
...@@ -30,6 +30,7 @@ ...@@ -30,6 +30,7 @@
namespace qmt { namespace qmt {
class CustomRelation;
class StereotypeController; class StereotypeController;
class StereotypeIcon; class StereotypeIcon;
class Toolbar; class Toolbar;
...@@ -49,6 +50,7 @@ public: ...@@ -49,6 +50,7 @@ public:
private: private:
void onStereotypeIconParsed(const StereotypeIcon &stereotypeIcon); void onStereotypeIconParsed(const StereotypeIcon &stereotypeIcon);
void onRelationParsed(const CustomRelation &customRelation);
void onToolbarParsed(const Toolbar &toolbar); void onToolbarParsed(const Toolbar &toolbar);
ConfigControllerPrivate *d; ConfigControllerPrivate *d;
......
...@@ -27,12 +27,14 @@ ...@@ -27,12 +27,14 @@
#include <QObject> #include <QObject>
#include "qmt/infrastructure/exceptions.h" #include "qmt/infrastructure/exceptions.h"
#include "qmt/stereotype/customrelation.h"
#include "qmt/stereotype/toolbar.h" #include "qmt/stereotype/toolbar.h"
#include "sourcepos.h" #include "sourcepos.h"
#include <QPair> #include <QPair>
#include <QHash> #include <QHash>
#include <functional>
namespace qmt { namespace qmt {
...@@ -59,6 +61,17 @@ class QMT_EXPORT StereotypeDefinitionParser : public QObject ...@@ -59,6 +61,17 @@ class QMT_EXPORT StereotypeDefinitionParser : public QObject
Q_OBJECT Q_OBJECT
class StereotypeDefinitionParserPrivate; class StereotypeDefinitionParserPrivate;
class IconCommandParameter; class IconCommandParameter;
class Value;
enum Type {
Void,
Identifier,
String,
Int,
Float,
Boolean,
Color
};
public: public:
explicit StereotypeDefinitionParser(QObject *parent = 0); explicit StereotypeDefinitionParser(QObject *parent = 0);
...@@ -66,6 +79,7 @@ public: ...@@ -66,6 +79,7 @@ public:
signals: signals:
void iconParsed(const StereotypeIcon &stereotypeIcon); void iconParsed(const StereotypeIcon &stereotypeIcon);
void relationParsed(const CustomRelation &relation);
void toolbarParsed(const Toolbar &toolbar); void toolbarParsed(const Toolbar &toolbar);
public: public:
...@@ -78,12 +92,24 @@ private: ...@@ -78,12 +92,24 @@ private:
static QPair<int, IconCommandParameter> SCALED(int keyword); static QPair<int, IconCommandParameter> SCALED(int keyword);
static QPair<int, IconCommandParameter> FIX(int keyword); static QPair<int, IconCommandParameter> FIX(int keyword);
static QPair<int, IconCommandParameter> ABSOLUTE(int keyword); static QPair<int, IconCommandParameter> ABSOLUTE(int keyword);
void parseIconShape(StereotypeIcon *stereotypeIcon); static QPair<int, IconCommandParameter> BOOLEAN(int keyword);
QHash<int, ShapeValueF> parseIconShapeProperties(const QHash<int, IconCommandParameter> &parameters); IconShape parseIconShape();
QHash<int, IconCommandParameter> parseIconShapeProperties(const QHash<int, IconCommandParameter> &parameters);
void parseRelation(CustomRelation::Element element);
void parseRelationEnd(CustomRelation *relation);
void parseToolbar(); void parseToolbar();
void parseToolbarTools(Toolbar *toolbar); void parseToolbarTools(Toolbar *toolbar);
void parseToolbarTool(Toolbar::Tool *tool); void parseToolbarTool(const Toolbar *toolbar, Toolbar::Tool *tool);
template<typename T>
void parseEnums(const QList<QString> &identifiers, const QHash<QString, T> &identifierNames,
const SourcePos &sourcePos, std::function<void(T)> setter);
template<typename T>
void parseEnum(const QString &identifier, const QHash<QString, T> &identifierNames,
const SourcePos &sourcePos, std::function<void(T)> setter);
QString parseStringProperty(); QString parseStringProperty();
int parseIntProperty(); int parseIntProperty();
...@@ -92,6 +118,7 @@ private: ...@@ -92,6 +118,7 @@ private:
QList<QString> parseIdentifierListProperty(); QList<QString> parseIdentifierListProperty();
bool parseBoolProperty(); bool parseBoolProperty();
QColor parseColorProperty(); QColor parseColorProperty();
Value parseProperty();
QString parseStringExpression(); QString parseStringExpression();
qreal parseFloatExpression(); qreal parseFloatExpression();
...@@ -99,6 +126,7 @@ private: ...@@ -99,6 +126,7 @@ private:
QString parseIdentifierExpression(); QString parseIdentifierExpression();
bool parseBoolExpression(); bool parseBoolExpression();
QColor parseColorExpression(); QColor parseColorExpression();
Value parseExpression();
void expectBlockBegin(); void expectBlockBegin();
bool readProperty(Token *token); bool readProperty(Token *token);
......
...@@ -130,6 +130,7 @@ HEADERS += \ ...@@ -130,6 +130,7 @@ HEADERS += \
$$PWD/serializer/infrastructureserializer.h \ $$PWD/serializer/infrastructureserializer.h \
$$PWD/serializer/modelserializer.h \ $$PWD/serializer/modelserializer.h \
$$PWD/serializer/projectserializer.h \ $$PWD/serializer/projectserializer.h \
$$PWD/stereotype/customrelation.h \
$$PWD/stereotype/iconshape.h \ $$PWD/stereotype/iconshape.h \
$$PWD/stereotype/shape.h \ $$PWD/stereotype/shape.h \
$$PWD/stereotype/shapepaintvisitor.h \ $$PWD/stereotype/shapepaintvisitor.h \
...@@ -155,7 +156,7 @@ HEADERS += \ ...@@ -155,7 +156,7 @@ HEADERS += \
$$PWD/tasks/ielementtasks.h \ $$PWD/tasks/ielementtasks.h \
$$PWD/tasks/isceneinspector.h \ $$PWD/tasks/isceneinspector.h \
$$PWD/tasks/voidelementtasks.h \ $$PWD/tasks/voidelementtasks.h \
$$PWD/infrastructure/qmtassert.h $$PWD/infrastructure/qmtassert.h \
SOURCES += \ SOURCES += \
$$PWD/config/configcontroller.cpp \ $$PWD/config/configcontroller.cpp \
...@@ -258,6 +259,7 @@ SOURCES += \ ...@@ -258,6 +259,7 @@ SOURCES += \
$$PWD/serializer/infrastructureserializer.cpp \ $$PWD/serializer/infrastructureserializer.cpp \
$$PWD/serializer/modelserializer.cpp \ $$PWD/serializer/modelserializer.cpp \
$$PWD/serializer/projectserializer.cpp \ $$PWD/serializer/projectserializer.cpp \
$$PWD/stereotype/customrelation.cpp \
$$PWD/stereotype/iconshape.cpp \ $$PWD/stereotype/iconshape.cpp \
$$PWD/stereotype/shapepaintvisitor.cpp \ $$PWD/stereotype/shapepaintvisitor.cpp \
$$PWD/stereotype/shapes.cpp \ $$PWD/stereotype/shapes.cpp \
...@@ -277,7 +279,7 @@ SOURCES += \ ...@@ -277,7 +279,7 @@ SOURCES += \
$$PWD/tasks/diagramscenecontroller.cpp \ $$PWD/tasks/diagramscenecontroller.cpp \
$$PWD/tasks/finddiagramvisitor.cpp \ $$PWD/tasks/finddiagramvisitor.cpp \
$$PWD/tasks/findrootdiagramvisitor.cpp \ $$PWD/tasks/findrootdiagramvisitor.cpp \
$$PWD/tasks/voidelementtasks.cpp $$PWD/tasks/voidelementtasks.cpp \
RESOURCES += \ RESOURCES += \
$$PWD/resources/resources.qrc $$PWD/resources/resources.qrc
/****************************************************************************
**
** Copyright (C) 2016 Jochen Becher
** Contact: https://www.qt.io/licensing/
**
** This file is part of Qt Creator.
**
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 3 as published by the Free Software
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
**
****************************************************************************/
#include "customrelation.h"
namespace qmt {
void CustomRelation::End::setEndItems(const QList<QString> &endItems)
{
m_endItems = endItems;
}
void CustomRelation::End::setRole(const QString &role)
{
m_role = role;
}
void CustomRelation::End::setCardinality(const QString &cardinality)
{
m_cardinality = cardinality;
}
void CustomRelation::End::setNavigable(bool navigable)
{
m_navigable = navigable;
}
void CustomRelation::End::setRelationship(CustomRelation::Relationship relationship)
{
m_relationship = relationship;
}
void CustomRelation::End::setHead(CustomRelation::Head head)
{
m_head = head;
}
void CustomRelation::End::setShape(const IconShape &shape)
{
m_shape = shape;
}
CustomRelation::CustomRelation()
{
}
CustomRelation::~CustomRelation()
{
}
bool CustomRelation::isNull() const
{
return m_id.isEmpty();
}
void CustomRelation::setElement(CustomRelation::Element element)
{
m_element = element;
}
void CustomRelation::setId(const QString &id)
{
m_id = id;
}
void CustomRelation::setTitle(const QString &title)
{
m_title = title;
}
void CustomRelation::setEndItems(const QList<QString> &endItems)
{
m_endItems = endItems;
}
void CustomRelation::setStereotypes(const QSet<QString> &stereotypes)
{
m_stereotypes = stereotypes;
}
void CustomRelation::setName(const QString &name)
{
m_name = name;
}
void CustomRelation::setDirection(CustomRelation::Direction direction)
{
m_direction = direction;
}
void CustomRelation::setEndA(const CustomRelation::End &end)
{
m_endA = end;
}
void CustomRelation::setEndB(const CustomRelation::End &end)
{
m_endB = end;
}
void CustomRelation::setShaftPattern(CustomRelation::ShaftPattern shaftPattern)
{
m_shaftPattern = shaftPattern;
}
void CustomRelation::setColorType(CustomRelation::ColorType colorType)
{
m_colorType = colorType;
}
void CustomRelation::setColor(const QColor &color)
{
m_color = color;
}
} // namespace qmt
/****************************************************************************
**
** Copyright (C) 2016 Jochen Becher
** Contact: https://www.qt.io/licensing/
**
** This file is part of Qt Creator.
**
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 3 as published by the Free Software
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
**
****************************************************************************/
#pragma once
#include "iconshape.h"
#include <QString>
#include <QList>
#include <QSet>
#include <QColor>
namespace qmt {
class QMT_EXPORT CustomRelation
{
public:
enum class Element {
Relation,
Dependency,
Inheritance,
Association
};
enum class Direction {
AtoB,
BToA,
Bi
};
enum class Relationship {
Association,
Aggregation,
Composition
};
enum class ShaftPattern {
Solid,
Dash,
Dot,
DashDot,
DashDotDot
};
enum class Head {
None,
Shape,
Arrow,
Triangle,
FilledTriangle,
Diamond,
FilledDiamond
};
enum class ColorType {
EndA,
EndB,
Custom
};
class End {
public:
QList<QString> endItems() const { return m_endItems; }
void setEndItems(const QList<QString> &endItems);
QString role() const { return m_role; }
void setRole(const QString &role);
QString cardinality() const { return m_cardinality; }
void setCardinality(const QString &cardinality);
bool navigable() const { return m_navigable; }
void setNavigable