对齐圆内的矩形

时间:2016-11-21 14:48:37

标签: javascript canvas fabricjs

我有一个圆圈,我需要用矩形填充这个圆圈。像这样的东西: enter image description here

是否有一些算法或建议从哪里开始? 我使用fabric.js进行绘图。这是playground。但是,问题更多的是数学可能。我希望我应该有一些公式。

2 个答案:

答案 0 :(得分:2)

我现在将“足够接近”:从半径中减去矩形长度,然后将结果乘以2π。那就是内圆周。现在将其除以矩形宽度(并向下舍入)以获得矩形的数量。将其除以360°以获得绘制它们的角度。

以下是演示:http://jsbin.com/napecagado/edit?js,output

答案 1 :(得分:1)

我更新了您提供的JSBin文件。我已经在很多细节中注释了代码,所以我在这里没有解释。

var canvas = new fabric.Canvas(document.querySelector('#my-canvas'));

var circleRadius = 250;
var boxHeight = 30;
var boxWidth = 150;

function createCircleAndBoxes(radius, boxHeight, boxWidth) {
  var circle = new fabric.Circle({
    radius: circleRadius,
    fill: '#f3aa25',
    stroke: '#333'
  });
  canvas.add(circle);

  // Calculates the center of the circle
  circle.left = (canvas.width - circle.width) / 2;
  circle.top = (canvas.height - circle.width) / 2;

  // The inner lines of the boxes make a circle
  // Calculate the circumference of this circle.
  // By dividing the height of the box by the calculated circumference
  // We can get the number of boxes needed
  var innerCircumference = 2 * Math.PI * (circleRadius - boxWidth);
  var roughBoxCount = Math.floor(innerCircumference / boxHeight);

  // Each box is placed exactly at the center of the circle
  var calculatedTop = circle.top + (circle.height / 2) - 1;
  var calculatedLeft = circle.left + (circle.width / 2) + 1;
  // By changing the origin to a negative point away from the box,
  // the box is translated. Also, all rotatopms are done from this point
  // The trick however is that, the origin point is calculated
  // as a percentage of the height and width. For instance, 0.5 means center
  // Therefore, we align the origin point with the circle center and 
  // calculate the offset as a percentage
  var calculatedOriginX = (boxWidth - circleRadius) / boxWidth;
  var calculatedOriginY = (boxHeight / 2) / boxHeight;

  // Since we have the number of boxes needed, we can calculate
  // what's the angle each box needs to be rotated
  var calculatedAngle = 360 / roughBoxCount;

  // Combine all these, and you got your requirement
  for(var i = 0; i<roughBoxCount; i++) {    
    var rect  = new fabric.Rect({
        angle: calculatedAngle * i,
        top: calculatedTop,
        left: calculatedLeft,
        centeredRotation: false,
        originX: calculatedOriginX,
        originY: calculatedOriginY,
        width: boxWidth,
        height: boxHeight,
        fill: '#e3e3e3',
        stroke: '#333'
    });
    canvas.add(rect);
  }
}

createCircleAndBoxes(circleRadius, boxHeight, boxWidth);

了解翻译,旋转和中心点计算,这是此类开发的关键。我的方法与'user348173'的上述答案略有不同。但我想,两者都值得通过

Updated JSBin