/******************************************************************************* * Copyright (c) 2012 Association for Decentralized Information Management in * Industry THTH ry. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * VTT Technical Research Centre of Finland - initial API and implementation *******************************************************************************/ package org.simantics.modeling.flags; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; import org.simantics.db.ReadGraph; import org.simantics.db.Resource; import org.simantics.db.Statement; import org.simantics.db.WriteGraph; import org.simantics.db.common.request.IndexRoot; import org.simantics.db.common.utils.OrderedSetUtils; import org.simantics.db.exception.DatabaseException; import org.simantics.diagram.stubs.DiagramResource; import org.simantics.diagram.stubs.G2DResource; import org.simantics.diagram.synchronization.graph.AddElement; import org.simantics.diagram.synchronization.graph.CopyAdvisorUtil; import org.simantics.g2d.elementclass.FlagClass; import org.simantics.layer0.Layer0; import org.simantics.modeling.ModelingResources; import org.simantics.scl.commands.Commands; import org.simantics.structural.stubs.StructuralResource2; /** * @author Hannu Niemistö */ public class ExpandFlags { static class Connector { Resource element; Resource terminal; public Connector(Resource element, Resource terminal) { this.element = element; this.terminal = terminal; } } private static ArrayList getConnectors(ReadGraph g, Resource connection) throws DatabaseException { StructuralResource2 STR = StructuralResource2.getInstance(g); ArrayList result = new ArrayList(); for(Resource connector : g.getObjects(connection, STR.IsConnectedTo)) { for(Statement stat : g.getStatements(connector, STR.Connects)) if(!connection.equals(stat.getObject())) { result.add(new Connector(stat.getObject(), g.getInverse(stat.getPredicate()))); } } return result; } public static Resource[] expandFlag(WriteGraph graph, Resource flag) throws DatabaseException { return (Resource[])Commands.get(graph, "Simantics/Flag/expandFlag") .execute(graph, graph.syncRequest(new IndexRoot(flag)), flag); } /** * @param graph * @param flag * @return the flags that result from the expansion operation * @throws DatabaseException */ public static Resource[] expandFlagWithoutMetadata(WriteGraph graph, Resource flag) throws DatabaseException { DiagramResource DIA = DiagramResource.getInstance(graph); G2DResource G2D = G2DResource.getInstance(graph); StructuralResource2 STR = StructuralResource2.getInstance(graph); Layer0 L0 = Layer0.getInstance(graph); ModelingResources MOD = ModelingResources.getInstance(graph); // Find joins and check if this is multiflag Collection joins_ = graph.getObjects(flag, DIA.FlagIsJoinedBy); if(joins_.size() <= 1) return Resource.NONE; // Nothing to do // Analyze expanded flag Resource diagram = OrderedSetUtils.getSubjects(graph, flag).iterator().next(); Resource flagType = graph.getSingleObject(flag, DIA.HasFlagType); double[] transform = graph.getRelatedValue(flag, DIA.HasTransform); Resource connector = graph.getSingleObject(flag, DIA.Flag_ConnectionPoint); Statement connectsStatement = null; for(Statement temp : graph.getStatements(connector, STR.Connects)) if(!flag.equals(temp.getObject())) { connectsStatement = temp; break; } if(connectsStatement == null) return Resource.NONE; Resource arrowType = connectsStatement.getPredicate(); Resource diagramConnection = connectsStatement.getObject(); Resource connection = graph.getSingleObject(diagramConnection, MOD.DiagramConnectionToConnection); ArrayList connectors = getConnectors(graph, diagramConnection); if(connectors.size()==2) { Iterator it = connectors.iterator(); while(it.hasNext()) { if(it.next().element.equals(flag)) it.remove(); } } Resource diagramRelation = connectors.size()!=1 ? null : connectors.get(0).terminal; Resource connectionPoint = diagramRelation == null ? null : graph.getPossibleObject(diagramRelation, MOD.DiagramConnectionRelationToConnectionRelation); Resource element=connectors.size()==1 ? connectors.get(0).element : null, component=null, connectionType=null; Resource routeLine = null; if(connectionPoint != null && !graph.isInstanceOf(connectionPoint, L0.FunctionalRelation)) { component = graph.getSingleObject(element, MOD.ElementToComponent); connectionType = graph.getSingleObject(diagramConnection, STR.HasConnectionType); } else if(element != null && graph.isInstanceOf(element, MOD.ReferenceElement)) { component = graph.getSingleObject(element, MOD.HasParentComponent); connectionPoint = graph.getSingleObject(element, MOD.HasReferenceRelation); connectionType = graph.getSingleObject(diagramConnection, STR.HasConnectionType); } else { routeLine = graph.getSingleObject(connector, DIA.AreConnected); if(!graph.isInstanceOf(routeLine, DIA.RouteLine)) { Resource otherConnector = routeLine; routeLine = graph.newResource(); graph.deny(connector, DIA.AreConnected, otherConnector); graph.claim(routeLine, L0.InstanceOf, DIA.RouteLine); graph.claim(diagramConnection, DIA.HasInteriorRouteNode, routeLine); graph.claimLiteral(routeLine, DIA.HasPosition, transform[4]-FlagClass.DEFAULT_WIDTH*0.5); graph.claimLiteral(routeLine, DIA.IsHorizontal, false); graph.claim(routeLine, DIA.AreConnected, connector); graph.claim(routeLine, DIA.AreConnected, otherConnector); } } Resource[] joins = joins_.toArray(new Resource[joins_.size()]); Resource[] flags = new Resource[joins.length]; final double flagSeparation = FlagClass.DEFAULT_HEIGHT; flags[0] = flag; for(int i=1;i groups) throws DatabaseException { DiagramResource DIA = DiagramResource.getInstance(graph); ModelingResources MOD = ModelingResources.getInstance(graph); Layer0 L0 = Layer0.getInstance(graph); Resource diagram = graph.getPossibleObject(composite, MOD.CompositeToDiagram); if(diagram == null) return; for(Resource element : graph.getObjects(diagram, L0.ConsistsOf)) if(graph.isInstanceOf(element, DIA.Flag)) { Collection objects = (Collection) graph.getObjects(element, DIA.FlagIsJoinedBy); if (objects.size() > 1) { groups.add(element); } } } }