JSFiddle - React, Tailwind, and code Playground

by koutsenko

HTML

<canvas id="c" width="300" height="300" style="border:1px solid"></canvas>

JavaScript

var colorMaps=[
	'333333',
	'520000',
	'786217',
	'3D220C',
	'DEDBD8'
];

BRANCH_DEFORMATION = 30;
BRANCH_MAXLENGTH = 200;
BRANCH_MAXWIDTH = 70;
BRANCH_OUTGROWTH = 4;
BRANCH_CONSTRICTION = 1.5;
BRANCH_COLOR = '#' + colorMaps[Math.ceil(rand(0, colorMaps.length - 1))];

var canvasElement = document.getElementById('c'),
    c = canvasElement.getContext('2d');

   
Number.prototype.degree = function () {
    return this * Math.PI / 180;
};

drawStick(50, 40, 80, 5, 60, 0.6);
drawStick(130, 42, 40, 5, 100, 180.0);

function rand(min, max) {
    return Math.random() * (max - min) + min;
}

/**
 * @param {Number} x гор. коорд. начала ветви
 * @param {Number} y верт. коорд. начала ветви
 * @param {Number} l длина ветви
 * @param {Number} w ширина ветви
 * @param {Number} d кривизна ветви
 * @param {Number} r поворот
 * Отрисовка ветвей.
 */
function drawStick(x, y, l, w, d, r) {

    //Save canvas and transform
    c.save();
    c.translate(x, y);
    c.rotate(r.degree());

    //Set X and Y for null  
    x = 0;
    y = w / -2;

    //Draw stick path
    c.beginPath();
    c.moveTo(x, y);
    c.bezierCurveTo(x, y, x + l / 2, y + d, x + l, y + (w - (w / BRANCH_CONSTRICTION)) / 2);
    c.lineTo(x + l, y + w / BRANCH_CONSTRICTION + (w - (w / BRANCH_CONSTRICTION)) / 2);
    c.bezierCurveTo(x + l, y + w / BRANCH_CONSTRICTION + (w - (w / BRANCH_CONSTRICTION)) / 2, x + l / 2, y + w + d, x, y + w);
    c.lineTo(x, y);
    c.closePath();

    //Draw arc on stick 
    c.arc(x + l, y + w / BRANCH_CONSTRICTION / 2 + (w - (w / BRANCH_CONSTRICTION)) / 2, w / BRANCH_CONSTRICTION / 2, 0 * Math.PI, 2 * Math.PI, false);

    //Fill stick
    c.fillStyle = BRANCH_COLOR;
    c.fill();

    //Restore canvas 
    c.restore();
}