/******************************************************************************* * Copyright (c) 2017 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: * Semantum Oy - #7119 initial API and implementation *******************************************************************************/ package org.simantics.diagram.adapter; import java.awt.Shape; import java.awt.geom.AffineTransform; import java.util.Collection; import org.simantics.diagram.content.ResourceTerminal; import org.simantics.g2d.diagram.handler.Topology.Terminal; import org.simantics.g2d.element.IElement; import org.simantics.g2d.element.handler.TerminalLayout; import org.simantics.g2d.element.handler.TerminalTopology; import org.simantics.g2d.element.handler.impl.ObjectTerminal; import org.simantics.g2d.element.handler.impl.Terminals; import org.simantics.scenegraph.g2d.IG2DNode; import org.simantics.scenegraph.g2d.nodes.SingleElementNode; import org.simantics.scenegraph.utils.NodeUtil; /** * A {@link TerminalTopology} and more specifically a {@link TerminalLayout} * implementation that relies primarily on the scene graph and only secondarily * on its internal datastructures to resolve terminal locations. This implementation * is used to support dynamic terminals. * * @author Antti Villberg * @since 1.29.0 */ public class DefinedElementTerminals extends Terminals { private static final long serialVersionUID = -726490868093887444L; public DefinedElementTerminals(Collection ts) { super(ts); } private IG2DNode findResourceTerminalNode(IG2DNode node, ResourceTerminal rt) { return (IG2DNode) NodeUtil.forChildrenDeep(node, SingleElementNode.class, n -> { Object key = n.getKey(); if (rt.getResource().equals(key)) { IG2DNode[] children = n.getSortedNodes(); if (children.length > 0) return children[0]; return n; } return null; }); } @Override public AffineTransform getTerminalPosition(IElement e, Terminal t) { if (t instanceof ResourceTerminal) { ResourceTerminal rt = (ResourceTerminal) t; IG2DNode node = e.getHint(DefinedElementHandler.KEY_SG_NODE); if (node != null) { IG2DNode n = findResourceTerminalNode(node, rt); if (n != null) { return n.getTransform(); } } } ObjectTerminal ti = terminalMap.get(t); if (ti == null) return null; return ti.getTransform(); } @Override public Shape getTerminalShape(IElement e, Terminal t) { if (t instanceof ResourceTerminal) { ResourceTerminal rt = (ResourceTerminal) t; IG2DNode node = e.getHint(DefinedElementHandler.KEY_SG_NODE); if (node != null) { IG2DNode n = findResourceTerminalNode(node, rt); if (n != null) { return n.getBoundsInLocal(); } } } return super.getTerminalShape(e, t); } }