如何在矩形区域计算和放置圆圈?

时间:2014-07-25 07:38:56

标签: javascript jquery math canvas jcanvas

我正在尝试在Canvas区域绘制一些图表。我的问题是......

我要绘制1-4个(或更多)圆圈。画布尺寸类似于500 x 400像素。我现在如何计算每个圆的最大半径以将所有圆放置在此画布上并获得每个圆的位置(中心x / y)?那么每个圆圈可以最佳地放置在该区域上,彼此之间有一些余量?

这里有一些示例屏幕,向您展示我的意思......

placing four circles Place the circles like a table

非常感谢!

3 个答案:

答案 0 :(得分:2)

计算可以使用的最大半径

    var numberOfSections = 4;
    var width = 500;
    var height = 400;
    var R = Math.sqrt((width * height) / numberOfSections) / 2

    var MX = Math.round(width / (R * 2)); // max amount of squares that can fit on the width
    var MY = Math.round(height / (R * 2)); // max amount of squares that can fit on the height

var skipLast = 0;
var numOfCalculatedCircles = MX*MY;
if(numOfCalculatedCircles != numberOfSections) {

    if(numOfCalculatedCircles < numberOfSections) {
        console.log('numOfCalculatedCircles',numOfCalculatedCircles);
        MX = MX + Math.ceil((numberOfSections - numOfCalculatedCircles)/MY);
        if(MX*MY != numberOfSections) {
            skipLast = Math.abs(MX*MY - numberOfSections);
        }
    } else {
        skipLast = numOfCalculatedCircles - numberOfSections;;
    }

    console.log('MX*MY',MX*MY);
}
// recalculate the radius for X
if (R * 2 * MX > width) {
    R = (width/2) / MX;
}

// recalculate the radius for Y
if (R * 2 * MY > height) {
    R = (height/2) / MY
}

计算X和Y的边距:

    var circlesWidth = R * 2 * MX;
    var circlesHeight = R * 2 * MY;

    var marginX = 0;
    var marginY = 0;
    if (circlesWidth < width) {
        marginX = (width - circlesWidth) / 2
    }
    if (circlesHeight < height) {
        marginY = (height - circlesHeight) / 2
    }

之后你可以计算中心:

var RY = marginY + R;
var radiusPadding = 10;

for (var i = 0; i < MY; i++) {
    var RX = marginX + R;
    for (var j = 0; j < MX; j++) {
        if(i === MY - 1) {
          if(j === MX - skipLast) {
            break;
          }
        }
        canvas.drawArc({
            fromCenter: true,
            strokeStyle: 'red',
            strokeWidth: 1,
            start: 0,
            end: 360,
            radius: R - radiusPadding,
            x: RX,
            y: RY
        });

        RX += 2 * R;
    }

    RY += 2 * R;
}

希望这有帮助。

更新:它仍然不完整,但可能适用于此特定示例:http://jsfiddle.net/dhM96/4/

答案 1 :(得分:1)

您没有提供足够的展示位置限制。

无论如何,假设沿着矩形边缘的F像素和圆圈之间的f的可用空间,X上的最大半径为Rx = (Width - 2 F - (Nx-1) f) / 2且{{1} },Y。 (R y = (Height - 2F - (Ny-1) f) / 2水平圈,Nx垂直。)取两者中最小的一个。

中心位于Ny(F + (2 Rx + f) Ix + Rx, F + (2 Ry + f) Iy + Ry)0 <= Ix < Nx

答案 2 :(得分:-1)

你要问的Knapsack problem很难解决。在您的情况下,最好的方法是使用给定的表,例如 http://www.packomania.com 。如果可以,请将自己限制在一个正方形。