Skip to content

Commit

Permalink
[272] Add state transition compartment and fix action creation in states
Browse files Browse the repository at this point in the history
Bug: eclipse-syson#272
Signed-off-by: Gwendal Daniel <gwendal.daniel@obeosoft.com>
  • Loading branch information
gdaniel committed May 17, 2024
1 parent 53cd41e commit d8173d9
Show file tree
Hide file tree
Showing 10 changed files with 294 additions and 117 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
- https://github.com/eclipse-syson/syson/issues/274[#274] [import] Namespace.getImportedMemberships method now prevents name collisions
- https://github.com/eclipse-syson/syson/issues/271[#271] [diagrams] Remove non end Usages from AllocationDefinition ends compartment
- https://github.com/eclipse-syson/syson/issues/229[#229] [diagrams] Prevent circular containment of nested parts including self containment
- https://github.com/eclipse-syson/syson/issues/272[#272] [statetransition-view] Add "state transition" compartment and fix the graphical creation of actions in StateDefinition and StateUsage

=== Improvements

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,9 +34,10 @@
import org.eclipse.syson.diagram.common.view.tools.ToolSectionDescription;
import org.eclipse.syson.diagram.statetransition.view.edges.TransitionEdgeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.CompartmentNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.CompositeStateDefinitionNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.DefinitionNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.FakeNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.PackageNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.StateTransitionCompartmentNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.StateTransitionViewEmptyDiagramNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.nodes.UsageNodeDescriptionProvider;
import org.eclipse.syson.sysml.SysmlPackage;
Expand Down Expand Up @@ -95,9 +96,13 @@ public RepresentationDescription create(IColorProvider colorProvider) {
diagramElementDescriptionProviders.add(new StateTransitionViewEmptyDiagramNodeDescriptionProvider(colorProvider));
diagramElementDescriptionProviders.add(new PackageNodeDescriptionProvider(colorProvider));
diagramElementDescriptionProviders.add(new TransitionEdgeDescriptionProvider(colorProvider));
diagramElementDescriptionProviders
.add(new StateTransitionCompartmentNodeDescriptionProvider(SysmlPackage.eINSTANCE.getStateDefinition(), SysmlPackage.eINSTANCE.getDefinition_OwnedState(), colorProvider, this.nameGenerator));
diagramElementDescriptionProviders
.add(new StateTransitionCompartmentNodeDescriptionProvider(SysmlPackage.eINSTANCE.getStateUsage(), SysmlPackage.eINSTANCE.getUsage_NestedState(), colorProvider, this.nameGenerator));

DEFINITIONS.forEach(definition -> {
diagramElementDescriptionProviders.add(new CompositeStateDefinitionNodeDescriptionProvider(definition, colorProvider));
diagramElementDescriptionProviders.add(new DefinitionNodeDescriptionProvider(definition, colorProvider));
});

USAGES.forEach(usage -> {
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
/*******************************************************************************
* Copyright (c) 2024 Obeo.
* This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v2.0
* which accompanies this distribution, and is available at
* https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Obeo - initial API and implementation
*******************************************************************************/
package org.eclipse.syson.diagram.statetransition.view.nodes;

import java.util.ArrayList;
import java.util.List;

import org.eclipse.emf.ecore.EClass;
import org.eclipse.sirius.components.view.builder.IViewDiagramElementFinder;
import org.eclipse.sirius.components.view.builder.providers.IColorProvider;
import org.eclipse.sirius.components.view.diagram.NodeDescription;
import org.eclipse.sirius.components.view.diagram.NodeToolSection;
import org.eclipse.syson.diagram.common.view.nodes.AbstractDefinitionNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.STVDescriptionNameGenerator;
import org.eclipse.syson.diagram.statetransition.view.StateTransitionViewDiagramDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.services.StateTransitionViewNodeToolSectionSwitch;
import org.eclipse.syson.sysml.SysmlPackage;

/**
* Node description provider for all SysMLv2 Definitions elements in the State Transition View diagram.
*
* @author gdaniel
*/
public class DefinitionNodeDescriptionProvider extends AbstractDefinitionNodeDescriptionProvider {

public DefinitionNodeDescriptionProvider(EClass eClass, IColorProvider colorProvider) {
super(eClass, colorProvider, new STVDescriptionNameGenerator());
}

@Override
protected List<NodeDescription> getReusedChildren(IViewDiagramElementFinder cache) {
var reusedChildren = new ArrayList<NodeDescription>();

StateTransitionViewDiagramDescriptionProvider.COMPARTMENTS_WITH_LIST_ITEMS.forEach((type, listItems) -> {
if (type.equals(this.eClass)) {
listItems.forEach(eReference -> {
cache.getNodeDescription(this.nameGenerator.getCompartmentName(type, eReference)).ifPresent(reusedChildren::add);
});
}
});
if (this.eClass.equals(SysmlPackage.eINSTANCE.getStateDefinition())) {
cache.getNodeDescription(this.nameGenerator.getFreeFormCompartmentName(this.eClass, SysmlPackage.eINSTANCE.getDefinition_OwnedState())).ifPresent(reusedChildren::add);
}
return reusedChildren;
}

@Override
protected List<NodeDescription> getAllNodeDescriptions(IViewDiagramElementFinder cache) {
var allNodes = new ArrayList<NodeDescription>();

StateTransitionViewDiagramDescriptionProvider.DEFINITIONS.forEach(definition -> cache.getNodeDescription(this.nameGenerator.getNodeName(definition)).ifPresent(allNodes::add));
StateTransitionViewDiagramDescriptionProvider.USAGES.forEach(usage -> cache.getNodeDescription(this.nameGenerator.getNodeName(usage)).ifPresent(allNodes::add));
cache.getNodeDescription(this.nameGenerator.getNodeName(SysmlPackage.eINSTANCE.getPackage())).ifPresent(allNodes::add);
return allNodes;
}

@Override
protected List<NodeToolSection> getToolSections(NodeDescription nodeDescription, IViewDiagramElementFinder cache) {
StateTransitionViewNodeToolSectionSwitch toolSectionSwitch = new StateTransitionViewNodeToolSectionSwitch();
toolSectionSwitch.doSwitch(this.eClass);
return toolSectionSwitch.getNodeToolSections();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
import org.eclipse.syson.diagram.common.view.nodes.AbstractFakeNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.STVDescriptionNameGenerator;
import org.eclipse.syson.diagram.statetransition.view.StateTransitionViewDiagramDescriptionProvider;
import org.eclipse.syson.sysml.SysmlPackage;

/**
* Fake Node Description allowing to store other Node Descriptions that will be reused by other Node Descriptions.
Expand All @@ -47,6 +48,11 @@ protected List<NodeDescription> getChildrenDescription(IViewDiagramElementFinder
StateTransitionViewDiagramDescriptionProvider.COMPARTMENTS_WITH_LIST_ITEMS.forEach((type, listItems) -> {
listItems.forEach(eReference -> cache.getNodeDescription(nameGenerator.getCompartmentName(type, eReference)).ifPresent(childrenNodes::add));
});

// don't forget to add custom compartments
cache.getNodeDescription(nameGenerator.getFreeFormCompartmentName(SysmlPackage.eINSTANCE.getStateDefinition(), SysmlPackage.eINSTANCE.getDefinition_OwnedState()))
.ifPresent(childrenNodes::add);
cache.getNodeDescription(nameGenerator.getFreeFormCompartmentName(SysmlPackage.eINSTANCE.getStateUsage(), SysmlPackage.eINSTANCE.getUsage_NestedState())).ifPresent(childrenNodes::add);
return childrenNodes;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
/*******************************************************************************
* Copyright (c) 2024 Obeo.
* This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v2.0
* which accompanies this distribution, and is available at
* https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Obeo - initial API and implementation
*******************************************************************************/
package org.eclipse.syson.diagram.statetransition.view.nodes;

import java.util.ArrayList;
import java.util.List;

import org.eclipse.emf.ecore.EClass;
import org.eclipse.emf.ecore.EReference;
import org.eclipse.sirius.components.view.builder.IViewDiagramElementFinder;
import org.eclipse.sirius.components.view.builder.providers.IColorProvider;
import org.eclipse.sirius.components.view.diagram.DiagramDescription;
import org.eclipse.sirius.components.view.diagram.InsideLabelDescription;
import org.eclipse.sirius.components.view.diagram.InsideLabelPosition;
import org.eclipse.sirius.components.view.diagram.InsideLabelStyle;
import org.eclipse.sirius.components.view.diagram.NodeDescription;
import org.eclipse.sirius.components.view.diagram.NodePalette;
import org.eclipse.sirius.components.view.diagram.SynchronizationPolicy;
import org.eclipse.syson.diagram.common.view.nodes.AbstractCompartmentNodeDescriptionProvider;
import org.eclipse.syson.diagram.statetransition.view.tools.StateTransitionCompartmentNodeToolProvider;
import org.eclipse.syson.sysml.SysmlPackage;
import org.eclipse.syson.util.AQLConstants;
import org.eclipse.syson.util.IDescriptionNameGenerator;
import org.eclipse.syson.util.SysMLMetamodelHelper;
import org.eclipse.syson.util.ViewConstants;

/**
* Used to create the 'state transition' free form compartment that contains nested/owned states.
*
* @author gdaniel
*/
public class StateTransitionCompartmentNodeDescriptionProvider extends AbstractCompartmentNodeDescriptionProvider {

public static final String STATE_COMPARTMENT_NAME = "state transition";

private final String name;

public StateTransitionCompartmentNodeDescriptionProvider(EClass eClass, EReference eReference, IColorProvider colorProvider, IDescriptionNameGenerator nameGenerator) {
super(eClass, eReference, colorProvider, nameGenerator);
this.name = nameGenerator.getFreeFormCompartmentName(this.eClass, this.eReference);
}

@Override
public NodeDescription create() {
return this.diagramBuilderHelper.newNodeDescription()
.childrenLayoutStrategy(this.diagramBuilderHelper.newFreeFormLayoutStrategyDescription().build())
.defaultHeightExpression("150")
.defaultWidthExpression(ViewConstants.DEFAULT_NODE_WIDTH)
.domainType(SysMLMetamodelHelper.buildQualifiedName(SysmlPackage.eINSTANCE.getElement()))
.insideLabel(this.createInsideLabelDescription())
.isHiddenByDefaultExpression("aql:true")
.name(this.name)
.semanticCandidatesExpression(AQLConstants.AQL_SELF)
.style(this.createCompartmentNodeStyle())
.userResizable(false)
.synchronizationPolicy(SynchronizationPolicy.SYNCHRONIZED)
.build();
}

@Override
public void link(DiagramDescription diagramDescription, IViewDiagramElementFinder cache) {
cache.getNodeDescription(this.name).ifPresent(nodeDescription -> {
cache.getNodeDescription(this.nameGenerator.getNodeName(SysmlPackage.eINSTANCE.getStateUsage())).ifPresent(nodeDescription.getReusedChildNodeDescriptions()::add);
nodeDescription.setPalette(this.createCompartmentPalette(cache));
});
}

@Override
protected List<NodeDescription> getDroppableNodes(IViewDiagramElementFinder cache) {
List<NodeDescription> droppableNodes = new ArrayList<>();
cache.getNodeDescription(this.nameGenerator.getNodeName(SysmlPackage.eINSTANCE.getStateUsage())).ifPresent(droppableNodes::add);
return droppableNodes;
}

@Override
protected InsideLabelDescription createInsideLabelDescription() {
return this.diagramBuilderHelper.newInsideLabelDescription()
.labelExpression(STATE_COMPARTMENT_NAME)
.position(InsideLabelPosition.TOP_CENTER)
.style(this.createInsideLabelStyle())
.build();
}

@Override
protected InsideLabelStyle createInsideLabelStyle() {
return this.diagramBuilderHelper.newInsideLabelStyle()
.displayHeaderSeparator(false)
.fontSize(12)
.italic(true)
.labelColor(this.colorProvider.getColor(ViewConstants.DEFAULT_LABEL_COLOR))
.showIcon(false)
.withHeader(false)
.build();
}

@Override
protected NodePalette createCompartmentPalette(IViewDiagramElementFinder cache) {
var palette = this.diagramBuilderHelper.newNodePalette().dropNodeTool(this.createCompartmentDropFromDiagramTool(cache));

// Do not use getItemCreationToolProvider because the compartment contains multiple creation tools.
palette.nodeTools(new StateTransitionCompartmentNodeToolProvider(false).create(cache),
new StateTransitionCompartmentNodeToolProvider(true).create(cache)
);

return palette.toolSections(this.defaultToolsFactory.createDefaultHideRevealNodeToolSection()).build();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,9 @@ protected List<NodeDescription> getReusedChildren(IViewDiagramElementFinder cach
});
}
});
if (this.eClass.equals(SysmlPackage.eINSTANCE.getStateUsage())) {
cache.getNodeDescription(this.nameGenerator.getFreeFormCompartmentName(this.eClass, SysmlPackage.eINSTANCE.getUsage_NestedState())).ifPresent(reusedChildren::add);
}
return reusedChildren;
}

Expand Down
Loading

0 comments on commit d8173d9

Please sign in to comment.