我正試圖在畫布區域繪製一些圖表。我的問題如下...如何計算並在矩形區域上放置圓圈?
我有1-4(或更多)圈畫。畫布大小像500 x 400像素。我現在如何計算每個圓的最大半徑以將所有這些畫布放在這個畫布上並獲取每個圓的位置(中心x/y)?那麼每個圈子都可以優化放置在相互之間有一定邊距的區域?
這裏一些示例屏幕來展示一下我的意思是......
非常感謝!
我正試圖在畫布區域繪製一些圖表。我的問題如下...如何計算並在矩形區域上放置圓圈?
我有1-4(或更多)圈畫。畫布大小像500 x 400像素。我現在如何計算每個圓的最大半徑以將所有這些畫布放在這個畫布上並獲取每個圓的位置(中心x/y)?那麼每個圈子都可以優化放置在相互之間有一定邊距的區域?
這裏一些示例屏幕來展示一下我的意思是......
非常感謝!
要計算最大半徑可以使用
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/
你問的Knapsack problem很難解決。在你的情況最好的辦法是使用給定的表,如http://www.packomania.com。如果可以的話,限制自己到廣場。
你沒有給夠你放置約束。
無論如何,假設沿着矩形邊緣F
像素和圓圈之間f
的自由空間,對X
最大半徑是Rx = (Width - 2 F - (Nx-1) f)/2
和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
,0 <= Iy < Ny
。
看起來很有趣,但我不知道如何修改它。我嘗試了下面的方法,但是它畫了6個圈子,大到半徑和錯誤的位置。 var numberOfSections = data.length,//當前:4 \t \t \t R = Math。sqrt((cWidth * cHeight)/ numberOfSections)/ 2, \t \t \t centers = []; \t \t \t 爲\t(VAR X = R,Y = R; X + = 2 * R){ \t \t \t如果(X> = cWidth){ \t \t \t \t X = R; \t \t \t \t y + = R; \t \t \t \t if(y> = cHeight)break; \t \t} \t \t \t canvas.drawArc({ \t \t \t \t fromCenter:真, \t \t \t \t的StrokeStyle:的StrokeStyle, \t \t \t \t strokeWidth:strokeWidth, \t \t \t \t開始:0, \t \t \t \t端:360, \t \t \t \t半徑:R, \t \t \t \t X:X, \t \t \t \tÿ:Y \t \t \t}); \t \t} – HR123
把它放在小提琴上:http://jsfiddle.net/hn7u7/ – HR123
@ HR123對不起,這個答案是不完整的,回答你的問題比我想象的更復雜。我創建了一個可以用作參考的jsfiddle:http://jsfiddle.net/hn7u7/3/。如果這對你有用,我會更新我的答案。 – lexmihaylov