Search in sources :

Example 56 with KVector

use of org.eclipse.elk.core.math.KVector in project elk by eclipse.

the class DotImporter method transformAttribute.

/**
 * Apply the property given in the attribute to a property holder.
 *
 * @param target the property holder that receives the new property
 * @param attribute a Graphviz attribute that contains the property
 * @param transData transformation data
 */
private void transformAttribute(final IPropertyHolder target, final Attribute attribute, final IDotTransformationData<GraphvizModel, ElkNode> transData) {
    String name = attribute.getName();
    String value = trimValue(attribute);
    try {
        if (Attributes.LAYOUT.equals(name)) {
            Command command = Command.parse(value);
            if (command != Command.INVALID) {
                target.setProperty(CoreOptions.ALGORITHM, "org.eclipse.elk.algorithm.graphviz." + command);
            } else {
                target.setProperty(CoreOptions.ALGORITHM, value);
            }
        } else if (Attributes.WIDTH.equals(name)) {
            target.setProperty(PROP_DEF_WIDTH, Float.valueOf(value) * DotExporter.DPI);
        } else if (Attributes.HEIGHT.equals(name)) {
            target.setProperty(PROP_DEF_HEIGHT, Float.valueOf(value) * DotExporter.DPI);
        } else if (Attributes.FIXEDSIZE.equals(name)) {
            Boolean fixedSize = Boolean.valueOf(value);
            target.setProperty(CoreOptions.NODE_SIZE_CONSTRAINTS, fixedSize ? SizeConstraint.fixed() : EnumSet.of(SizeConstraint.MINIMUM_SIZE));
        } else if (Attributes.NODESEP.equals(name)) {
            target.setProperty(CoreOptions.SPACING_NODE_NODE, Double.valueOf(value));
        } else if (Attributes.PACK.equals(name)) {
            target.setProperty(CoreOptions.SEPARATE_CONNECTED_COMPONENTS, Boolean.valueOf(value));
        } else if (Attributes.PAD.equals(name)) {
            if (value.indexOf(',') >= 0) {
                KVector pad = new KVector();
                pad.parse(value);
                ElkPadding padding = new ElkPadding(pad.x / 2, pad.y / 2);
                target.setProperty(CoreOptions.PADDING, padding);
            } else {
                target.setProperty(CoreOptions.PADDING, new ElkPadding(Float.valueOf(value)));
            }
        } else if (Attributes.RANKDIR.equals(name)) {
            if (value.equals("TB")) {
                target.setProperty(CoreOptions.DIRECTION, Direction.DOWN);
            } else if (value.equals("BT")) {
                target.setProperty(CoreOptions.DIRECTION, Direction.UP);
            } else if (value.equals("LR")) {
                target.setProperty(CoreOptions.DIRECTION, Direction.RIGHT);
            } else if (value.equals("RL")) {
                target.setProperty(CoreOptions.DIRECTION, Direction.LEFT);
            }
        } else if (Attributes.SPLINES.equals(name)) {
            if (value.equals("spline") || value.equals("true")) {
                target.setProperty(CoreOptions.EDGE_ROUTING, EdgeRouting.SPLINES);
            } else if (value.equals("polyline") || value.equals("line") || value.equals("false")) {
                target.setProperty(CoreOptions.EDGE_ROUTING, EdgeRouting.POLYLINE);
            } else if (value.equals("ortho")) {
                target.setProperty(CoreOptions.EDGE_ROUTING, EdgeRouting.ORTHOGONAL);
            }
        } else if (Attributes.START.equals(name)) {
            if (value.startsWith("random")) {
                int random = 0;
                try {
                    random = Integer.parseInt(value.substring("random".length()));
                } catch (NumberFormatException e) {
                // ignore exception
                }
                target.setProperty(CoreOptions.RANDOM_SEED, random);
            }
        } else if (Attributes.WEIGHT.equals(name)) {
            target.setProperty(CoreOptions.PRIORITY, (int) Float.parseFloat(value));
        }
    } catch (NumberFormatException exception) {
        transData.log("Discarding attribute " + attribute.getName() + "=" + attribute.getValue() + " since its value could not be parsed correctly.");
    } catch (IllegalArgumentException exception) {
        transData.log("Discarding attribute " + attribute.getName() + "=" + attribute.getValue() + " since its value could not be parsed correctly.");
    }
}
Also used : KVector(org.eclipse.elk.core.math.KVector) ElkPadding(org.eclipse.elk.core.math.ElkPadding)

Example 57 with KVector

use of org.eclipse.elk.core.math.KVector in project elk by eclipse.

the class DotImporter method applyLayout.

/**
 * Apply layout to an edge and its labels.
 *
 * @param edge an edge
 * @param offset its offset in the graph
 * @param graph the Graphviz graph
 */
private void applyLayout(final ElkEdge edge, final KVector offset, final Graph graph) {
    EdgeStatement edgeStatement = (EdgeStatement) edge.getProperty(PROP_STATEMENT);
    if (edgeStatement.eContainer() == null) {
        // this can happen when an edge with multiple target declarations was found
        graph.getStatements().add(edgeStatement);
    }
    // transfer edge bend points and source / target points
    List<Attribute> attributes = edgeStatement.getAttributes();
    removeAttributes(attributes, Attributes.POS);
    if (!edge.getSections().isEmpty()) {
        StringBuilder bendpointString = new StringBuilder("\"");
        KVectorChain vectorChain = ElkUtil.createVectorChain(edge.getSections().get(0));
        ListIterator<KVector> chainIter = vectorChain.listIterator();
        while (chainIter.hasNext()) {
            KVector point = chainIter.next().add(offset);
            bendpointString.append(point.x);
            bendpointString.append(',');
            bendpointString.append(point.y);
            if (chainIter.hasNext()) {
                bendpointString.append(' ');
            }
        }
        bendpointString.append('\"');
        attributes.add(DotExporter.createAttribute(Attributes.POS, bendpointString.toString()));
    }
    // transfer label positions
    for (ElkLabel label : edge.getLabels()) {
        String attrKey = null;
        switch(label.getProperty(CoreOptions.EDGE_LABELS_PLACEMENT)) {
            case CENTER:
                attrKey = Attributes.LABELPOS;
                break;
            case HEAD:
                attrKey = Attributes.HEADLP;
                break;
            case TAIL:
                attrKey = Attributes.TAILLP;
                break;
        }
        if (attrKey != null) {
            removeAttributes(attributes, attrKey);
            double xpos = label.getX() + label.getWidth() / 2 + offset.x;
            double ypos = label.getY() + label.getHeight() / 2 + offset.y;
            String posString = "\"" + Double.toString(xpos) + "," + Double.toString(ypos) + "\"";
            attributes.add(DotExporter.createAttribute(attrKey, posString));
        }
    }
}
Also used : Attribute(org.eclipse.elk.alg.graphviz.dot.dot.Attribute) ElkLabel(org.eclipse.elk.graph.ElkLabel) KVectorChain(org.eclipse.elk.core.math.KVectorChain) KVector(org.eclipse.elk.core.math.KVector) EdgeStatement(org.eclipse.elk.alg.graphviz.dot.dot.EdgeStatement)

Example 58 with KVector

use of org.eclipse.elk.core.math.KVector in project elk by eclipse.

the class DotImporter method applyLayout.

/*---------- Layout Transfer KGraph to Dot ----------*/
/**
 * Apply layout to a parent node and its children.
 *
 * @param parent a parent node
 * @param offset the node's offset in the graph
 * @param graph the Graphviz graph
 */
private void applyLayout(final ElkNode parent, final KVector offset, final Graph graph) {
    for (ElkNode elknode : parent.getChildren()) {
        Statement statement = elknode.getProperty(PROP_STATEMENT);
        if (statement == null) {
            // the node was only declared implicitly - create an explicit declaration
            NodeStatement stm = DotFactory.eINSTANCE.createNodeStatement();
            Node node = DotFactory.eINSTANCE.createNode();
            node.setName(elknode.getProperty(PROP_ID));
            stm.setNode(node);
            graph.getStatements().add(stm);
            statement = stm;
        }
        if (statement instanceof NodeStatement) {
            List<Attribute> attributes = ((NodeStatement) statement).getAttributes();
            // transfer node position
            removeAttributes(attributes, Attributes.POS);
            double xpos = elknode.getX() + elknode.getWidth() / 2 + offset.x;
            double ypos = elknode.getY() + elknode.getHeight() / 2 + offset.y;
            String posString = "\"" + Double.toString(xpos) + "," + Double.toString(ypos) + "\"";
            attributes.add(DotExporter.createAttribute(Attributes.POS, posString));
            // transfer node size
            removeAttributes(attributes, Attributes.WIDTH);
            attributes.add(DotExporter.createAttribute(Attributes.WIDTH, elknode.getWidth() / DotExporter.DPI));
            removeAttributes(attributes, Attributes.HEIGHT);
            attributes.add(DotExporter.createAttribute(Attributes.HEIGHT, elknode.getHeight() / DotExporter.DPI));
        } else if (statement instanceof Subgraph) {
            applyLayout(elknode, new KVector(offset).add(elknode.getX(), elknode.getY()), graph);
        }
        for (ElkEdge elkedge : ElkGraphUtil.allOutgoingEdges(elknode)) {
            applyLayout(elkedge, offset, graph);
        }
    }
    // transfer graph size to bounding box
    List<Statement> statements;
    Statement graphStm = parent.getProperty(PROP_STATEMENT);
    if (graphStm instanceof Subgraph) {
        statements = ((Subgraph) graphStm).getStatements();
    } else {
        statements = graph.getStatements();
    }
    removeGraphAttributes(statements, Attributes.BOUNDINGBOX);
    String bbString = "\"0,0," + Double.toString(parent.getWidth()) + "," + Double.toString(parent.getHeight()) + "\"";
    statements.add(DotExporter.createAttribute(Attributes.BOUNDINGBOX, bbString));
}
Also used : ElkNode(org.eclipse.elk.graph.ElkNode) Attribute(org.eclipse.elk.alg.graphviz.dot.dot.Attribute) EdgeStatement(org.eclipse.elk.alg.graphviz.dot.dot.EdgeStatement) NodeStatement(org.eclipse.elk.alg.graphviz.dot.dot.NodeStatement) AttributeStatement(org.eclipse.elk.alg.graphviz.dot.dot.AttributeStatement) Statement(org.eclipse.elk.alg.graphviz.dot.dot.Statement) NodeStatement(org.eclipse.elk.alg.graphviz.dot.dot.NodeStatement) ElkNode(org.eclipse.elk.graph.ElkNode) Node(org.eclipse.elk.alg.graphviz.dot.dot.Node) Subgraph(org.eclipse.elk.alg.graphviz.dot.dot.Subgraph) KVector(org.eclipse.elk.core.math.KVector) ElkEdge(org.eclipse.elk.graph.ElkEdge)

Example 59 with KVector

use of org.eclipse.elk.core.math.KVector in project elk by eclipse.

the class DotImporter method transform.

/*---------- Transformation Dot to KGraph ----------*/
/**
 * Transform a Dot graph to a KNode.
 *
 * @param statements
 *            a list of Dot statements
 * @param parent
 *            a KNode
 * @param transData
 *            transformation data instance
 * @param nodeProps
 *            properties that are applied to all nodes
 * @param edgeProps
 *            properties that are applied to all edges
 */
private void transform(final List<Statement> statements, final ElkNode parent, final IDotTransformationData<GraphvizModel, ElkNode> transData, final IPropertyHolder nodeProps, final IPropertyHolder edgeProps) {
    DotSwitch<Object> statementSwitch = new DotSwitch<Object>() {

        public Object caseNodeStatement(final NodeStatement statement) {
            transformNode(statement, parent, transData, nodeProps);
            return null;
        }

        public Object caseEdgeStatement(final EdgeStatement statement) {
            transformEdge(statement, parent, transData, edgeProps);
            return null;
        }

        public Object caseSubgraph(final Subgraph subgraph) {
            ElkNode subElkNode = parent;
            if (subgraph.getName() != null && subgraph.getName().startsWith("cluster")) {
                subElkNode = transformNode(subgraph.getName(), parent, transData);
                if (subElkNode.getProperty(PROP_STATEMENT) != null) {
                    transData.log("Discarding cluster subgraph \"" + subgraph.getName() + "\" since its id is already used.");
                    return null;
                } else {
                    // the subgraph inherits all settings of its parent
                    subElkNode.copyProperties(parent);
                    subElkNode.setProperty(PROP_STATEMENT, subgraph);
                }
            }
            MapPropertyHolder subNodeProps = new MapPropertyHolder();
            subNodeProps.copyProperties(nodeProps);
            MapPropertyHolder subEdgeProps = new MapPropertyHolder();
            subEdgeProps.copyProperties(edgeProps);
            transform(subgraph.getStatements(), subElkNode, transData, subNodeProps, subEdgeProps);
            return null;
        }

        public Object caseAttributeStatement(final AttributeStatement statement) {
            switch(statement.getType()) {
                case GRAPH:
                    for (Attribute attr : statement.getAttributes()) {
                        caseAttribute(attr);
                    }
                    break;
                case NODE:
                    for (Attribute attr : statement.getAttributes()) {
                        transformAttribute(nodeProps, attr, transData);
                    }
                    break;
                case EDGE:
                    for (Attribute attr : statement.getAttributes()) {
                        transformAttribute(edgeProps, attr, transData);
                    }
                    break;
            }
            return null;
        }

        public Object caseAttribute(final Attribute attribute) {
            if (Attributes.MARGIN.equals(attribute.getName())) {
                ElkPadding padding = parent.getProperty(CoreOptions.PADDING);
                if (attribute.getValue().indexOf(',') >= 0) {
                    KVector value = new KVector();
                    try {
                        value.parse(attribute.getValue());
                        padding.setLeft((float) value.x);
                        padding.setRight((float) value.x);
                        padding.setTop((float) value.y);
                        padding.setBottom((float) value.y);
                    } catch (IllegalArgumentException exception) {
                        transData.log("Discarding attribute \"" + attribute.getName() + "\" since its value could not be parsed correctly.");
                    }
                } else {
                    try {
                        float value = Float.parseFloat(trimValue(attribute));
                        padding.setLeft(value);
                        padding.setRight(value);
                        padding.setTop(value);
                        padding.setBottom(value);
                    } catch (NumberFormatException exception) {
                        transData.log("Discarding attribute \"" + attribute.getName() + "\" since its value could not be parsed correctly.");
                    }
                }
            } else {
                transformAttribute(parent, attribute, transData);
            }
            return null;
        }
    };
    for (Statement statement : statements) {
        statementSwitch.doSwitch(statement);
    }
}
Also used : ElkNode(org.eclipse.elk.graph.ElkNode) Attribute(org.eclipse.elk.alg.graphviz.dot.dot.Attribute) NodeStatement(org.eclipse.elk.alg.graphviz.dot.dot.NodeStatement) EdgeStatement(org.eclipse.elk.alg.graphviz.dot.dot.EdgeStatement) NodeStatement(org.eclipse.elk.alg.graphviz.dot.dot.NodeStatement) AttributeStatement(org.eclipse.elk.alg.graphviz.dot.dot.AttributeStatement) Statement(org.eclipse.elk.alg.graphviz.dot.dot.Statement) MapPropertyHolder(org.eclipse.elk.graph.properties.MapPropertyHolder) EdgeStatement(org.eclipse.elk.alg.graphviz.dot.dot.EdgeStatement) AttributeStatement(org.eclipse.elk.alg.graphviz.dot.dot.AttributeStatement) Subgraph(org.eclipse.elk.alg.graphviz.dot.dot.Subgraph) KVector(org.eclipse.elk.core.math.KVector) ElkPadding(org.eclipse.elk.core.math.ElkPadding) DotSwitch(org.eclipse.elk.alg.graphviz.dot.dot.util.DotSwitch)

Example 60 with KVector

use of org.eclipse.elk.core.math.KVector in project elk by eclipse.

the class InteractiveCrossingMinimizer method getPos.

/**
 * Determine a vertical position for the given node.
 *
 * @param node a node
 * @param horizPos the horizontal position at which to measure (relevant for edges)
 * @return the vertical position used for sorting
 */
private double getPos(final LNode node, final double horizPos) {
    switch(node.getType()) {
        case LONG_EDGE:
            LEdge edge = (LEdge) node.getProperty(InternalProperties.ORIGIN);
            // reconstruct the original bend points from the node annotations
            KVectorChain bendpoints = edge.getProperty(InternalProperties.ORIGINAL_BENDPOINTS);
            if (bendpoints == null) {
                bendpoints = new KVectorChain();
            } else if (edge.getProperty(InternalProperties.REVERSED)) {
                bendpoints = KVectorChain.reverse(bendpoints);
            }
            // Check if we can determine the position just by using the source point, if we can determine it
            LPort source = node.getProperty(InternalProperties.LONG_EDGE_SOURCE);
            if (source != null) {
                KVector sourcePoint = source.getAbsoluteAnchor();
                if (horizPos <= sourcePoint.x) {
                    return sourcePoint.y;
                }
                bendpoints.addFirst(sourcePoint);
            }
            // Check if we can determine the position just by using the target point
            LPort target = node.getProperty(InternalProperties.LONG_EDGE_TARGET);
            if (target != null) {
                KVector targetPoint = target.getAbsoluteAnchor();
                if (targetPoint.x <= horizPos) {
                    return targetPoint.y;
                }
                bendpoints.addLast(targetPoint);
            }
            // Find the two points along the edge that the horizontal point lies between
            if (bendpoints.size() >= 2) {
                Iterator<KVector> pointIter = bendpoints.iterator();
                KVector point1 = pointIter.next();
                KVector point2 = pointIter.next();
                while (point2.x < horizPos && pointIter.hasNext()) {
                    point1 = point2;
                    point2 = pointIter.next();
                }
                return point1.y + (horizPos - point1.x) / (point2.x - point1.x) * (point2.y - point1.y);
            }
            break;
        case NORTH_SOUTH_PORT:
            // Get one of the ports the dummy node was created for, and its original node
            LPort originPort = (LPort) node.getPorts().get(0).getProperty(InternalProperties.ORIGIN);
            LNode originNode = originPort.getNode();
            switch(originPort.getSide()) {
                case NORTH:
                    // by respecting node successor constraints.
                    return originNode.getPosition().y;
                case SOUTH:
                    // Use the position of the node's southern side
                    return originNode.getPosition().y + originNode.getSize().y;
            }
            break;
    }
    // the fallback solution is to take the previous position of the node's anchor point
    return node.getInteractiveReferencePoint().y;
}
Also used : LEdge(org.eclipse.elk.alg.layered.graph.LEdge) KVectorChain(org.eclipse.elk.core.math.KVectorChain) LPort(org.eclipse.elk.alg.layered.graph.LPort) LNode(org.eclipse.elk.alg.layered.graph.LNode) KVector(org.eclipse.elk.core.math.KVector)

Aggregations

KVector (org.eclipse.elk.core.math.KVector)292 KVectorChain (org.eclipse.elk.core.math.KVectorChain)52 ElkNode (org.eclipse.elk.graph.ElkNode)49 LNode (org.eclipse.elk.alg.layered.graph.LNode)39 LPort (org.eclipse.elk.alg.layered.graph.LPort)37 ElkRectangle (org.eclipse.elk.core.math.ElkRectangle)36 LEdge (org.eclipse.elk.alg.layered.graph.LEdge)35 Test (org.junit.Test)30 ElkEdge (org.eclipse.elk.graph.ElkEdge)28 ElkLabel (org.eclipse.elk.graph.ElkLabel)27 ElkEdgeSection (org.eclipse.elk.graph.ElkEdgeSection)26 ElkPadding (org.eclipse.elk.core.math.ElkPadding)25 LLabel (org.eclipse.elk.alg.layered.graph.LLabel)20 PortSide (org.eclipse.elk.core.options.PortSide)19 ElkPort (org.eclipse.elk.graph.ElkPort)18 SizeConstraint (org.eclipse.elk.core.options.SizeConstraint)17 LGraph (org.eclipse.elk.alg.layered.graph.LGraph)15 ArrayList (java.util.ArrayList)13 Layer (org.eclipse.elk.alg.layered.graph.Layer)12 LMargin (org.eclipse.elk.alg.layered.graph.LMargin)11