JavaScript
语言:
JaveScriptBabelCoffeeScript
确定
var canvas = document.createElement('canvas'),
c = canvas.getContext('2d'),
title = document.createElement('h1');
canvas.style.transformOrigin = 'top left';
canvas.style.transform = 'scale(0.5, 0.5)';
document.body.appendChild(canvas);
title.innerHTML = 'Oera Linda Inspired Symbols';
document.body.appendChild(title);
var erase = function() {
c.fillStyle = "#dbcfaf";
c.fillRect(0, 0, canvas.width, canvas.height);
};
var shuffle = function() {
return 0.5 - Math.random();
};
var Symbol = function(x, y, radius) {
this.x = x;
this.y = y;
this.radius = radius;
this.halfRadius = this.radius / 2;
this.draw();
};
Symbol.ARC_NUM = 8;
Symbol.TOTAL_SEGS = 23;
Symbol.nodeMap = [
// [node index][list of node connections]
[7, 1, 9, 11], // 0
[0, 2, 11, 13], // 1
[1, 3, 13, 15], // 2
[2, 4, 15, 17], // 3
[3, 5, 17, 19], // 4
[4, 6, 19, 21], // 5
[5, 7, 21, 23], // 6
[6, 0, 23, 9], // 7
[9, 10, 12, 14, 16, 18, 20, 22], // 8
[7, 0, 8], // 9
[11, 12, 14, 16, 18, 20, 22, 8], // 10
[0, 1, 10], // 11
[13, 14, 16, 18, 20, 22, 8, 10], // 12
[1, 2, 12], // 13
[15, 16, 18, 20, 22, 8, 10, 12], // 14
[2, 3, 14], // 15
[17, 18, 20, 22, 8, 10, 12, 14], // 16
[3, 4, 16], // 17
[19, 20, 22, 8, 10, 12, 14, 16], // 18
[4, 5, 18], // 19
[21, 22, 8, 10, 12, 14, 16, 18], // 20
[5, 6, 20], // 21
[23, 8, 10, 12, 14, 16, 18, 20], // 22
[6, 7, 22] // 23
];
Symbol.prototype = {
constructor: Symbol,
arcSegLength: (Math.PI * 2) / Symbol.ARC_NUM,
line: function(offset, isInner) {
var theta = this.arcSegLength * offset,
cos = Math.cos(theta),
sin = Math.sin(theta),
x1 = this.halfRadius * cos,
y1 = this.halfRadius * sin,
x2, y2;
if (isInner) {
x2 = 0;
y2 = 0;
} else {
x2 = this.radius * cos;
y2 = this.radius * sin;
}
c.beginPath();
c.moveTo(this.x + x1, this.y + y1);
c.lineTo(this.x + x2, this.y + y2);
c.stroke();
},
arc: function(offset) {
var step = this.arcSegLength * offset;
c.beginPath();
c.arc(this.x, this.y, this.radius, step, step + this.arcSegLength, false);
c.stroke();
},
drawAll: function() {
for (var i = 0; i <= Symbol.TOTAL_SEGS; i++) {
this[i]();
}
},
nextNode: function(currSeg) {
return Symbol.nodeMap[currSeg].concat().sort(shuffle)[0];
},
draw: function() {
var steps = 2 + Math.floor(Math.random() * Symbol.ARC_NUM),
start = Math.floor(Math.random() * Symbol.TOTAL_SEGS),
currSeg = start,
mem = {};
c.strokeStyle = "rgba(112,71,36,0.1)";
this.drawAll();
c.lineWidth = 2;
c.strokeStyle = "rgb(112,71,36)";
mem[currSeg] = true;
this[currSeg]();
for (var i = 0; i < steps; i++) {
currSeg = this.nextNode(currSeg);
// prevent dupes
while (mem[currSeg]) {
currSeg = this.nextNode(currSeg);
}
mem[currSeg] = true;
this[currSeg]();
}
}
};
// arcs:
for (var i = 0; i < Symbol.ARC_NUM; i++) {
(function(i) {
Symbol.prototype[i] = function() {
this.arc(i);
};
})(i);
}
for (var i = 8, j = 0; i <= Symbol.TOTAL_SEGS; i += 2, j++) {
// inner
(function(i, count) {
Symbol.prototype[i] = function() {
this.line(count, true);
};
})(i, j);
// outer
(function(i, count) {
Symbol.prototype[i] = function() {
this.line(count, false);
};
})(i + 1, j);
}
var render = function() {
var radius = 70,
diameter = radius * 2,
padding = 10,
size = diameter + padding * 2,
winWidth = window.innerWidth * 2,
winHeight = window.innerHeight * 2,
cols = Math.floor(winWidth / size),
rows = Math.floor(winHeight / size),
num = cols * rows,
offX = Math.abs(winWidth - (cols * size)) / 2,
offY = Math.abs(winHeight - (rows * size)) / 2;
for (var i = cols; i < num; i++) {
var x = offX + radius + i % cols * size;
var y = offY + radius + parseInt(i / cols) * size;
var s = new Symbol(x, y, radius);
}
};
var renderTimeout;
var rerender = function() {
clearInterval(renderTimeout);
renderTimeout = setTimeout(render, 500);
};
var resize = function(e) {
canvas.width = window.innerWidth * 2;
canvas.height = window.innerHeight * 2;
erase();
if (e) {
rerender();
}
};
window.addEventListener('resize', resize);
resize();
render();
document.addEventListener('click', function() {
erase();
render();
});