/* * Copyright 2016 Red Hat, Inc. and/or its affiliates. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.kie.workbench.common.stunner.client.lienzo.util; import com.ait.lienzo.client.core.shape.IPrimitive; import com.ait.lienzo.client.core.shape.Picture; import com.ait.lienzo.client.core.shape.wires.MagnetManager; import com.ait.lienzo.client.core.shape.wires.WiresLayoutContainer; import com.ait.lienzo.client.core.shape.wires.WiresShape; import com.ait.lienzo.client.core.types.BoundingBox; import com.ait.lienzo.client.core.types.LinearGradient; import org.kie.workbench.common.stunner.core.client.shape.HasChildren; import org.kie.workbench.common.stunner.core.client.shape.Shape; import org.kie.workbench.common.stunner.core.client.shape.view.ShapeView; import org.kie.workbench.common.stunner.core.client.util.ShapeUtils; public class LienzoShapeUtils { public static void scalePicture(final Picture picture, final double width, final double height) { final BoundingBox bb = picture.getBoundingBox(); final double[] scale = LienzoUtils.getScaleFactor(bb.getWidth(), bb.getHeight(), width, height); picture.setScale(scale[0], scale[1]); } public static WiresLayoutContainer.Layout getWiresLayout(final HasChildren.Layout layout) { switch (layout) { case CENTER: return WiresLayoutContainer.Layout.CENTER; case LEFT: return WiresLayoutContainer.Layout.LEFT; case RIGHT: return WiresLayoutContainer.Layout.RIGHT; case TOP: return WiresLayoutContainer.Layout.TOP; case BOTTOM: return WiresLayoutContainer.Layout.BOTTOM; } throw new UnsupportedOperationException("Unsupported layout [" + layout.name() + "]"); } public static LinearGradient getLinearGradient(final String startColor, final String endColor, final Double width, final Double height) { final LinearGradient linearGradient = new LinearGradient(0, width, 0, -height / 2); linearGradient.addColorStop(1, endColor); linearGradient.addColorStop(0, startColor); return linearGradient; } /** * Obtain the magnet indexes on the source and target shapes. * The resulting index values are on the min distance between the magnets, which is calculated * by basic trigonometry on the cartesian coordinates area. * To avoid using the magnets on shape's corners, only some concrete magnets will be allowed as result. As * arc's and line's magnet points are based cartesian cardinality and it is quite similar * on both cases ( see https://www.lienzo-core.com/lienzo-ks/#CARDINAL_INTERSECT ), * this implementation will consider only the odd magnet index values as results. * TODO: This is enough for the current line/arc support in stunner's shapes, but consider * improving this behavior on the future. */ public static int[] getDefaultMagnetsIndex(final WiresShape sourceShape, final WiresShape targetShape) { final MagnetManager.Magnets sourceMagnets = sourceShape.getMagnets(); final MagnetManager.Magnets targetMagnets = targetShape.getMagnets(); int sMagnet = 0; int tMagnet = 0; double dist = Double.MAX_VALUE; for (int x = 0; x < sourceMagnets.size(); x++) { if (isOddNumber(x)) { final IPrimitive<?> sourceControl = sourceMagnets.getMagnet(x).getControl(); final double sX = sourceControl.getX(); final double sY = sourceControl.getY(); for (int y = 0; y < targetMagnets.size(); y++) { if (isOddNumber(y)) { final IPrimitive<?> targetControl = targetMagnets.getMagnet(y).getControl(); final double tX = targetControl.getX(); final double tY = targetControl.getY(); final double _d = ShapeUtils.dist(sX, sY, tX, tY); if (_d < dist) { dist = _d; sMagnet = x; tMagnet = y; } } } } } return new int[]{sMagnet, tMagnet}; } public static int[] getDefaultMagnetsIndex(final Shape sourceShape, final Shape targetShape) { final ShapeView<?> sourceView = sourceShape.getShapeView(); final ShapeView<?> targetView = targetShape.getShapeView(); if (sourceView instanceof WiresShape && targetView instanceof WiresShape) { return getDefaultMagnetsIndex((WiresShape) sourceView, (WiresShape) targetView); } return new int[]{0, 0}; } private static boolean isOddNumber(final int i) { return i % 2 > 0; } }