algorithm - 如何为凹多边形生成回声路径

标签 algorithm path polygon

我需要一种算法来绘制任意多边形的回声路径。如果多边形是凸的,问题就很容易解决。要理解我的意思,请看下面的图片,黑色是原始多边形,红色是从原始多边形生成的回声多边形。 convex polygon echo demonstration

d 是给定的回声路径之间的距离

β 角度很容易计算已知的顶点坐标

如您所见,对于每个顶点,我们可以计算 L,从而为下一个回声路径提供新的顶点。

问题是当我们在某个点有凹多边形时,我们会得到一张自交叉多边形的丑陋图片。请看看这张照片。 enter image description here

我想要做的是生成没有自交叉部分的回声多边形,即没有带有虚线的部分。算法或 java 代码会很有帮助。谢谢。

编辑

只需添加一段代码即可按照评论中的要求为凸多边形生成回声路径。

public List<MyPath> createEchoCoCentral( List<Point> pointsOriginal, float encoderEchoDistance, int appliqueEchoCount){

    List<Point> contourPoints = pointsOriginal;
    List<MyPath> echoPaths = new ArrayList<>();
    for (int round = 0; round < appliqueEchoCount; round++) {

        List<Point> echoedPoints = new ArrayList<>();
        int size = contourPoints.size()+1;//+1 because we connect end to start

        Point previousPoint = contourPoints.get(contourPoints.size() - 1);
        for (int i = 0; i < size; i++) {
            Point currentPoint;
            if (i == contourPoints.size()) {
                currentPoint = new Point(contourPoints.get(0));
            } else {
                currentPoint = contourPoints.get(i);
            }
            final Point nextPoint;
            if (i + 1 == contourPoints.size()) {
                nextPoint = contourPoints.get(0);
            } else if (i == contourPoints.size()) {
                nextPoint = contourPoints.get(1);
            } else {
                nextPoint = contourPoints.get(i + 1);
            }
            if (currentPoint.x == previousPoint.x && currentPoint.y == previousPoint.y) continue;
            if (currentPoint.x == nextPoint.x && currentPoint.y == nextPoint.y) continue;

            // signs needed o determine to which side of polygon new point will go
            float currentSlope = (float) (Math.atan((previousPoint.y - currentPoint.y) / (previousPoint.x - currentPoint.x)));
            float signX = Math.signum((previousPoint.x - currentPoint.x));
            float signY = Math.signum((previousPoint.y - currentPoint.y));
            signX = signX == 0 ? 1 : signX;
            signY = signY == 0 ? 1 : signY;

            float nextSignX = Math.signum((currentPoint.x - nextPoint.x));
            float nextSignY = Math.signum((currentPoint.y - nextPoint.y));
            nextSignX = nextSignX == 0 ? 1 : nextSignX;
            nextSignY = nextSignY == 0 ? 1 : nextSignY;

            float nextSlope = (float) (Math.atan((currentPoint.y - nextPoint.y) / (currentPoint.x - nextPoint.x)));
            float nextSlopeD = (float) Math.toDegrees(nextSlope);

            //calculateMidAngle - is a bit tricky function that calculates angle between two adjacent edges
            double S = calculateMidAngle(currentSlope, nextSlope, signX, signY, nextSignX, nextSignY);
            Point p2 = new Point();

            double ew = encoderEchoDistance / Math.cos(S - (Math.PI / 2));
            p2.x = (int) (currentPoint.x + (Math.cos(currentSlope - S)) * ew * signX);
            p2.y = (int) (currentPoint.y + (Math.sin(currentSlope - S)) * ew * signX);

            echoedPoints.add(p2);
            previousPoint = currentPoint;


        }

        //createPathFromPoints just creates MyPath objects from given Poins set
        echoPaths.add(createPathFromPoints(echoedPoints));
        //remove last point since it was just to connect end to first point
        echoedPoints.remove(echoedPoints.size() - 1);
        contourPoints = echoedPoints;
    }
    return echoPaths;
}

最佳答案

您正在寻找 straight skeleton :


StraightSkeleton
<支持> (图片来自Wikipedia。)


关于algorithm - 如何为凹多边形生成回声路径,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38702828/

相关文章:

c - c语言如何连接两个字符串

ios - 铿锵错误 : Linker command when integrating AdColony sdk in iPhone app

algorithm - 使用 GLSL 组成图 block 的纹理坐标

algorithm - 具有 heaviside/step-function 的神经网络学习算法

c# - 文件路径中正斜杠(/)和反斜杠(\)的区别

javascript - 如何在 SVG 多边形元素上添加图钉标记图标?

java - 如何在Java中绘制像素完美的旋转矩形?

python - 使用 Python 对网格内的总线长求和

algorithm - 渐近符号 - n (log n) (log n) 简化了吗?

python - 在 Python 中保存文件时,我应该将连接的文件路径放在哪里?