使用随机颜色创建随机矩形,不使用javascript重叠

时间:2016-02-16 14:36:44

标签: javascript html css canvas

如何使用javascript在HTML中创建这样的内容? enter image description here

实际上我知道如何在HTML中创建矩形但是想要做这样的事情。 HTML画布可以是任何大小,但是无论何时加载页面,都会生成具有随机大小和颜色的多个正方形而不重叠。当我尝试这样做时,以列表形式生成矩形。我是一名网络开发人员(面向rails的ruby),但对这些javascript的东西不熟悉。任何帮助将不胜感激。

html:

<body>
    <div id="randBlock" >
    </div>
</body>

的javascript:

(function makeDiv(){
    var divsize = ((Math.random()*100) + 50).toFixed();
    var color = '#'+ Math.round(0xffffff * Math.random()).toString(16);
    $newdiv = $('#randBlock').css({
        'width':divsize+'px',
        'height':divsize+'px',
        'background-color': color
    });

    var posx = (Math.random() * ($(document).width() - divsize)).toFixed();
    var posy = (Math.random() * ($(document).height() - divsize)).toFixed();

    $newdiv.css({
        'position':'absolute',
        'left':posx+'px',
        'top':posy+'px',
        'display':'none'
    }).appendTo( 'body' ).fadeIn(100).delay(300).fadeOut(200, function(){
       $(this).remove();
       makeDiv(); 
    }); 
})();

2 个答案:

答案 0 :(得分:3)

使用画布的解决方案(所以我理解了这个问题)。

内置碰撞检测isInside()

编辑:更好的随机支持,不会永远运行,来自Drawing a 1px thick line in canvas creates a 2px thick line的提示以及此答案的一点点Random Color generator in Javascript

&#13;
&#13;
function getRandomColor() {
    var color = '#';
    for (var i = 0; i < 6; i++) {
        color += (Math.random() * 16 | 0).toString(16);
    }
    return color;
}

function Point(x, y) {
    this.x = x;
    this.y = y;
}

function Rectangle(p1, p2) {
    this.p1 = p1;
    this.p2 = p2;
}

Rectangle.prototype.isInside = function (r) {
    function check(a, b) {
        return (
            a.p1.x <= b.p1.x && b.p1.x <= a.p2.x && a.p1.y <= b.p1.y && b.p1.y <= a.p2.y ||
            a.p1.x <= b.p2.x && b.p2.x <= a.p2.x && a.p1.y <= b.p2.y && b.p2.y <= a.p2.y ||
            a.p1.x <= b.p2.x && b.p2.x <= a.p2.x && a.p1.y <= b.p1.y && b.p1.y <= a.p2.y ||
            a.p1.x <= b.p1.x && b.p1.x <= a.p2.x && a.p1.y <= b.p2.y && b.p2.y <= a.p2.y
        );
    }
    return check(this, r) || check(r, this);
}

function generateRectangles() {
    function p() { return Math.random() * 300 | 0; }
    function s() { return 50 + Math.random() * 150 | 0; }

    var rectangles = [],
        r, size, x, y, isInside, i, counter = 0;

    for (i = 0; i < 20; i++) {
        counter = 0;
        do {
            counter++;
            x = p();
            y = p();
            size = s();
            r = new Rectangle(new Point(x, y), new Point(x + size, y + size));
            isInside = rectangles.some(function (a) {
                return a.isInside(r);
            });
        } while (isInside && counter < 1000);
        counter < 1000 && rectangles.push(r);
    }
    return rectangles;
}

function drawRectangles(rectangles) {
    var canvas = document.getElementById("canvas"),
        ctx = canvas.getContext("2d");

    rectangles.forEach(function (a) {
        ctx.lineWidth = 1;
        ctx.strokeRect(a.p1.x + 0.5, a.p1.y + 0.5, a.p2.x - a.p1.x - 1, a.p2.y - a.p1.y - 1);
        ctx.fillStyle = getRandomColor();
        ctx.fillRect(a.p1.x + 0.5, a.p1.y + 0.5, a.p2.x - a.p1.x - 1, a.p2.y - a.p1.y - 1);
    });
}

var rectangles = generateRectangles();
drawRectangles(rectangles);
&#13;
<canvas id="canvas" width="500" height="500"></canvas>
&#13;
&#13;
&#13;

答案 1 :(得分:1)

你已经有了随机位置绘制一个随机方格。从那里很容易去绘制很多 - 只需要一个循环来添加多个div。当然,那么你需要给每个人一个随机的id,但这很容易。问题是这将允许重叠。

最简单的情况:允许重叠

&#13;
&#13;
function makeDiv(i) {
  var divsize = ((Math.random() * 100) + 50).toFixed();
  var color = '#' + Math.round(0xffffff * Math.random()).toString(16);
  var posx = (Math.random() * ($(document).width() - divsize)).toFixed();
  var posy = (Math.random() * ($(document).height() - divsize)).toFixed();
  var divid = 'randBlock' + i;

  $('#randBlock').append("<div id='" + divid + "'>");
  $('#' + divid).css({
    'width': divsize + 'px',
    'height': divsize + 'px',
    'background-color': color,
    'position': 'absolute',
    'left': posx + 'px',
    'top': posy + 'px'
  });
}

for (var i = 0; i < 10; ++i) {
  makeDiv(i);
}
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<body>
  <div id="randBlock">
  </div>
</body>
&#13;
&#13;
&#13;

如果你想保证它没有重叠,你还有很多工作要做,除非你能做一些CSS魔法,这很有可能,但我不是意识到这一点。您必须跟踪每个方块的位置和大小,并且只将结果拟合到清晰的区域。

根据您的具体要求,您的算法会有所不同。您将不得不有一些约束 - 无论是最大尺寸的正方形,重叠的要求,您想要适合的最大平方数,还是允许正方形变得越来越小。我将为您提供其中两个的口头演练。这是网格创意的工作片段。根据您在评论中添加的内容,这可能就足够了。

您已经构建了固定大小,因此最好的想法是使用该大小作为基础,并创建一个网格。在这种情况下,您知道每个gridsquare可以有一个正方形。有一个存储每个gridsquare位置的数组,并随机选择(1到该数组的长度) - 1.在该gridsquare中,拟合一个正方形,与您当前的函数非常相似。它的大小是你已经设置的最大值,它在该框中的位置可以根据大小随机。

网格化案例

&#13;
&#13;
var fixedScale = 100;
var fixedConstant = 50;
var fixedMax = fixedScale + fixedConstant;
var gridCols = (($(document).width() / fixedMax) + 1).toFixed();
var gridRows = (($(document).height() / fixedMax) + 1).toFixed();
var grid = [];
for (var row = 0; row < gridRows; ++row) {
  for (var col = 0; col < gridCols; ++col) {
    var index = row * gridCols + col;
    grid[index] = {row: row, col: col};
  }
}

function makeDiv(i) {
  var gridId = Math.floor(Math.random() * grid.length);
  
  var divsize = ((Math.random() * fixedScale) + fixedConstant).toFixed();
  console.log(gridId + ", grid.length = " + grid.length);
  var color = '#' + Math.round(0xffffff * Math.random()).toString(16);
  var posx = grid[gridId].col * fixedMax;
  var posy = grid[gridId].row * fixedMax;
  var offsetx = (Math.random() * (fixedMax - divsize)).toFixed();
  var offsety = (Math.random() * (fixedMax - divsize)).toFixed();
  posx = +posx + +offsetx;
  posy = +posy + +offsety;
  var divid = 'randBlock' + i;

  grid.splice(gridId, 1);
  
  $('#randBlock').append("<div id='" + divid + "'>");
  $('#' + divid).css({
    'width': divsize + 'px',
    'height': divsize + 'px',
    'background-color': color,
    'position': 'absolute',
    'left': posx + 'px',
    'top': posy + 'px'
  });
}

for (var i = 0; i < 10; ++i) {
  makeDiv(i);
}
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<body>
  <div id="randBlock">
  </div>
</body>
&#13;
&#13;
&#13;

您可以使用以下事实获得无限(但正在缩小的方块):每当您将一个方块添加到空白区域时,它将在该区域留下四个剩余空间的矩形。每当你制作一个彩色方块时,你实际上可以制作5个div:彩色方块,顶部空白区域,右侧,底部和左侧。使用特定类对空的属性进行属性。然后,查看所有具有&#34;空的&#34; class,并将最大大小设置为空div的最大值。当您创建下一个彩色方块时,选择一个至少与方块一样大的随机div。

显然,这些代码并非完全无足轻重。您在需求和约束中做出的选择将对您的编码工作产生巨大影响。