Created for the February 2019 CodePen Challenge
A Pen by Kevin LEVRON on CodePen.
| <svg id="svg"></svg> |
| let width, height, cx, cy; | |
| let svg = document.getElementById('svg'); | |
| function init() { | |
| onResize(); | |
| window.addEventListener('resize', onResize, false); | |
| for (let i = 0; i < 100; i++) { | |
| createFlower(Math.floor(4 + rnd(12)), rnd(width), rnd(height), 5 + rnd(10)); | |
| } | |
| let mouseDown = false; | |
| document.body.addEventListener('mousedown', e => { mouseDown = true; }); | |
| document.body.addEventListener('mouseup', e => { mouseDown = false; }); | |
| document.body.addEventListener('mouseleave', e => { mouseDown = false; }); | |
| document.body.addEventListener('mousemove', e => { | |
| let size = 5 + rnd(5); | |
| if (mouseDown) size *= 2; | |
| createFlower(Math.floor(4 + rnd(12)), e.clientX + rnd(20, true), e.clientY + rnd(20, true), size); | |
| }); | |
| } | |
| function createFlower(nbVertexes, x, y, s) { | |
| let opacity = 0.5 + rnd(0.5); | |
| let group = document.createElementNS('http://www.w3.org/2000/svg', 'g'); | |
| group.setAttributeNS(null, 'transform', `translate(${x}, ${y})`); | |
| group.setAttributeNS(null, 'style', `opacity:${opacity};`); | |
| svg.appendChild(group); | |
| let duration = 0.5 + rnd(3); | |
| let innerGroup = document.createElementNS('http://www.w3.org/2000/svg', 'g'); | |
| innerGroup.setAttributeNS(null, 'class', 'flower'); | |
| innerGroup.setAttributeNS(null, 'style', `animation-duration:${duration}s;`); | |
| group.appendChild(innerGroup); | |
| let polygon = document.createElementNS('http://www.w3.org/2000/svg', 'polygon'); | |
| let fill = randomColor({ format: 'rgb' }); | |
| polygon.setAttributeNS(null, 'points', polygonPoints(nbVertexes, 0, 0, s, 0)); | |
| polygon.setAttributeNS(null, 'style', `fill:${fill};`); | |
| innerGroup.appendChild(polygon); | |
| const dt = 2 * Math.PI / nbVertexes; | |
| // fill = randomColor({ luminosity: 'light', format: 'rgb' }); | |
| for (let i = 0; i < nbVertexes; i++) { | |
| let a = (i + 0.5) * dt; | |
| let r1 = Math.sin(Math.PI / nbVertexes) * s / Math.sin(Math.PI / 3); | |
| let r2 = Math.cos(Math.PI / nbVertexes) * s + Math.cos(Math.PI / 3) * r1; | |
| let tx = Math.cos(a) * r2; | |
| let ty = Math.sin(a) * r2; | |
| polygon = document.createElementNS('http://www.w3.org/2000/svg', 'polygon'); | |
| polygon.setAttributeNS(null, 'points', polygonPoints(3, tx, ty, r1, a)); | |
| polygon.setAttributeNS(null, 'style', `fill:${fill};`); | |
| innerGroup.appendChild(polygon); | |
| } | |
| } | |
| function onResize() { | |
| const r = svg.getBoundingClientRect(); | |
| width = r.width; | |
| height = r.height; | |
| cx = width / 2; | |
| cy = height / 2; | |
| } | |
| function ppoints(n, x, y, s, r) { | |
| const dt = 2 * Math.PI / n; | |
| let points = [], t, px, py; | |
| for (let i = 0; i < n; i++) { | |
| t = r + i * dt; | |
| px = x + Math.cos(t) * s; | |
| py = y + Math.sin(t) * s; | |
| points.push([px, py]); | |
| } | |
| return points; | |
| } | |
| function polygonPoints(n, x, y, s, r) { | |
| points = ppoints(n, x, y, s, r); | |
| return points.reduce((acc, point, i, a) => `${acc} ${point[0]},${point[1]}`); | |
| } | |
| function rnd(max, negative) { | |
| return negative ? Math.random() * 2 * max - max : Math.random() * max; | |
| } | |
| init(); |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/randomcolor/0.5.2/randomColor.min.js"></script> |
| body { | |
| margin: 0; | |
| width: 100%; | |
| height: 100%; | |
| } | |
| #svg { | |
| position: fixed; | |
| width: 100%; | |
| height: 100%; | |
| cursor: pointer; | |
| } | |
| polygon { | |
| stroke: #fff; | |
| stroke-width: 1; | |
| } | |
| .flower { | |
| animation-name: animation; | |
| animation-duration: 1s; | |
| animation-timing-function: ease-out; | |
| } | |
| @keyframes animation { | |
| 0% { | |
| opacity: 0; | |
| transform: scale(0.1, 0.1) rotateZ(0); | |
| } | |
| 100% { | |
| opacity: 1; | |
| transform: scale(1, 1) rotateZ(360deg); | |
| } | |
| } |
Created for the February 2019 CodePen Challenge
A Pen by Kevin LEVRON on CodePen.