Himmators
Himmators

Reputation: 15006

Randomizing an angle?

var elem = document.getElementById('canvas');
var context = elem.getContext('2d');

context.fillStyle = '#000';
context.lineWidth = 1;

var depth = 9;

function drawLine(x1, y1, x2, y2, brightness){
  context.moveTo(x1, y1);
  context.lineTo(x2, y2);
}

function drawTree(x1, y1, angle, depth){
  if (depth !== 0){
  	var thisAngle = angle*(Math.random()-0.5)
    var x2 = x1 + (Math.cos(thisAngle) * depth * 10.0);
    var y2 = y1 + (Math.sin(thisAngle) * depth * 10.0);
    drawLine(x1, y1, x2, y2, depth);
    drawTree(x2, y2, angle - 0.34906585, depth - 1);
    drawTree(x2, y2, angle + 0.34906585, depth - 1);
  }
}

context.beginPath();
drawTree(300, 500, -1.57, depth);
context.closePath();
context.stroke();
<html>
<body>
<canvas id="canvas" width="1000" height="700"></canvas>

</body>
</html>

I have a function that draws a tree-fractal in a canvas:

function drawTree(x1, y1, angle, depth){
  if (depth !== 0){
    var x2 = x1 + (Math.cos(angle) * depth * 10.0);
    var y2 = y1 + (Math.sin(angle) * depth * 10.0);
    drawLine(x1, y1, x2, y2, depth);
    drawTree(x2, y2, angle - 0.34906585, depth - 1);
    drawTree(x2, y2, angle + 0.34906585, depth - 1);
  }
}

enter image description here I'm trying to randomize the fractal a bit to make it look more organic. I tried this:

function drawTree(x1, y1, angle, depth){
  if (depth !== 0){
    var thisAngle = angle*(Math.random()-0.5)
    var x2 = x1 + (Math.cos(thisAngle) * depth * 10.0);
    var y2 = y1 + (Math.sin(thisAngle) * depth * 10.0);
    drawLine(x1, y1, x2, y2, depth);
    drawTree(x2, y2, angle - 0.34906585, depth - 1);
    drawTree(x2, y2, angle + 0.34906585, depth - 1);
  }
}

enter image description here

For some reason this seems to be biased torwards the value 0. The tree leans torwards the right. I don't understand why.

Upvotes: 9

Views: 123

Answers (1)

Alnitak
Alnitak

Reputation: 339786

You need to add a random offset (in the range ±0.5 or less) to your angle, not multiply by that factor.

var elem = document.getElementById('canvas');
var context = elem.getContext('2d');

context.fillStyle = '#000';
context.lineWidth = 1;

var depth = 9;

function drawLine(x1, y1, x2, y2, brightness){
  context.moveTo(x1, y1);
  context.lineTo(x2, y2);
}

function drawTree(x1, y1, angle, depth){
  if (depth !== 0) {
    var delta = Math.random()-0.5;
    var x2 = x1 + (Math.cos(angle + delta) * depth * 10.0);
    var y2 = y1 + (Math.sin(angle + delta) * depth * 10.0);
    drawLine(x1, y1, x2, y2, depth);
    drawTree(x2, y2, angle - 0.34906585, depth - 1);
    drawTree(x2, y2, angle + 0.34906585, depth - 1);
  }
}

context.beginPath();
drawTree(300, 500, -1.57, depth);
context.closePath();
context.stroke();
<html>
<body>
<canvas id="canvas" width="1000" height="700"></canvas>

</body>
</html>

You may also wish to experiment with changing the angle passed to the recursive calls (e.g. use the modified angle instead of the original one).

Upvotes: 7

Related Questions