diff --git a/Components/Backgrounds/Interactive-Hexagonal-Background/index.html b/Components/Backgrounds/Interactive-Hexagonal-Background/index.html new file mode 100644 index 00000000..e5251af5 --- /dev/null +++ b/Components/Backgrounds/Interactive-Hexagonal-Background/index.html @@ -0,0 +1,25 @@ + + + + + Interactive Hexagonal Background + + + + + + +
+ + + + + +
+ +
+ + + + + diff --git a/Components/Backgrounds/Interactive-Hexagonal-Background/script.js b/Components/Backgrounds/Interactive-Hexagonal-Background/script.js new file mode 100644 index 00000000..996b641e --- /dev/null +++ b/Components/Backgrounds/Interactive-Hexagonal-Background/script.js @@ -0,0 +1,214 @@ +// PARTICLES +const cvs = document.getElementById('particles'); +const ctx = cvs.getContext('2d'); + +cvs.width = window.innerWidth; +cvs.height = window.innerHeight; + +let particlesArray; + +let mouse = { + x: null, + y: null, + radius: 170 +} + +window.addEventListener('mousemove', function(event) { + mouse.x = event.x; + mouse.y = event.y; + mouse.radius = 170; + console.log(mouse.radius); +}); + +document.onmousemove = (function(event) { + var onmousestop = function() { + mouse.radius = 0; + }, thread; + + return function() { + clearTimeout(thread); + thread = setTimeout(onmousestop, 10); + }; +})(); + + +class Particle { + constructor(x, y, directionX, directionY, size, color) { + this.x = x; + this.y = y; + this.directionX = directionX; + this.directionY = directionY; + this.size = size; + this.color = color; + } + + draw() { + ctx.beginPath(); + ctx.arc(this.x, this.y, this.size, 0, Math.PI * 2, false); + ctx.fillStyle = '#72C100'; + ctx.fill(); + } + + update() { + if (this.x > cvs.width || this.x < 0) { + this.directionX = -this.directionX; + } + + if (this.y > cvs.height || this.y < 0) { + this.directionY = -this.directionY; + } + + let dx = mouse.x - this.x; + let dy = mouse.y - this.y; + let distance = Math.sqrt(dx * dx + dy * dy); + if (distance < mouse.radius + this.size) { + if (mouse.x < this.x && this.x < cvs.width - this.size * 10) { + this.x += 10; + } + + if (mouse.x > this.x && this.x > this.size * 10) { + this.x -= 10; + } + + if (mouse.y < this.y && this.y < cvs.height - this.size * 10) { + this.y += 10; + } + + if (mouse.y > this.y && this.y > this.size * 10) { + this.y -= 10; + } + } + this.x += this.directionX; + this.y += this.directionY; + + this.draw(); + } +} + +function init() { + particlesArray = []; + let numberOfParticles = (cvs.height * cvs.width) / 9000; + for (let i = 0; i < numberOfParticles * 0.25; i++) { + let size = (Math.random() * 35) + 1; + let x = (Math.random() * ((innerWidth - size * 2) - (size * 2)) + size * 2); + let y = (Math.random() * ((innerWidth - size * 2) - (size * 2)) + size * 2); + let directionX = (Math.random() * 5) - 2.5; + let directionY = (Math.random() * 5) - 2.5; + let color = '#72C100'; + particlesArray.push(new Particle(x, y, directionX, directionY, size, color)); + } +} + +function connect() { + let opacityValue = 1; + for (let i = 0; i < particlesArray.length; i++) { + for (let j = i; j < particlesArray.length; j++) { + let distance = ((particlesArray[i].x - particlesArray[j].x) * (particlesArray[i].x - particlesArray[j].x)) + ((particlesArray[i].y - particlesArray[j].y) * (particlesArray[i].y - particlesArray[j].y)); + + if (distance < (cvs.width/ 7) * (cvs.height / 7)) { + opacityValue = 1 - (distance / 20000); + ctx.strokeStyle = 'rgba(159, 253, 50,' + opacityValue + ')'; + ctx.lineWidth = 1; + ctx.beginPath(); + ctx.moveTo(particlesArray[i].x, particlesArray[i].y); + ctx.lineTo(particlesArray[j].x, particlesArray[j].y); + ctx.stroke(); + } + } + } +} + +function animate() { + requestAnimationFrame(animate); + ctx.clearRect(0, 0, innerWidth, innerHeight); + for (let i = 0; i < particlesArray.length; i++) { + particlesArray[i].update(); + } + connect(); +} + +window.addEventListener('resize', function() { + cvs.width = innerWidth; + cvs.height = this.innerHeight; + mouse.radius = 170; + init(); +}); + +window.addEventListener('mouseout', function() { + mouse.x = undefined; + mouse.y = undefined; +}); + +init(); +animate(); + +// HEXAGON GRID +function hexagonGrid() { + const HEXAGON_GRID = document.getElementById("hexagonGrid"); + const CONTAINER = HEXAGON_GRID.parentNode; + + let wall = { + width: CONTAINER.offsetWidth, + height: CONTAINER.offsetHeight + }; + + let rowsNumber = Math.ceil(wall.height / 80); + let columnsNumber = Math.ceil(wall.width / 100) + 1; + + HEXAGON_GRID.innerHTML = ""; + + for (let i = 0; i < rowsNumber; i++) { + let row = document.createElement("div"); + row.className = "row"; + HEXAGON_GRID.appendChild(row); + } + + let rows = HEXAGON_GRID.querySelectorAll(".row"); + + for (let i = 0; i < rows.length; i++) { + for (let j = 0; j < columnsNumber; j++) { + let hexagon = document.createElement("div"); + hexagon.className = "hexagon"; + rows[i].appendChild(hexagon); + } + } +} + +hexagonGrid(); + +window.addEventListener('resize', function() { + hexagonGrid(); +}); + +// FPS METER +(function () { + let previousTime = Date.now(); + let frames = 0; + let refreshRate = 1000; + + let fpsMeter = document.createElement("div"); + fpsMeter.id = "fpsMeter"; + document.body.appendChild(fpsMeter); + + requestAnimationFrame(function loop() { + const TIME = Date.now(); + frames++; + if (TIME > previousTime + refreshRate) { + let fps = Math.round((frames * refreshRate) / (TIME - previousTime)); + previousTime = TIME; + frames = 0; + fpsMeter.innerHTML = "FPS: " + fps * (1000 / refreshRate); + } + requestAnimationFrame(loop); + }); + + fpsMeter.style.position = "fixed"; + fpsMeter.style.top = "25px"; + fpsMeter.style.right = "25px"; + fpsMeter.style.background = "rgba(0, 0, 0, 0.5)"; + fpsMeter.style.padding = "10px"; + fpsMeter.style.color = "rgba(255, 255, 255, 0.75)"; + fpsMeter.style.fontFamily = "Monospace"; + fpsMeter.style.fontSize = "24px"; + fpsMeter.style.zIndex = "10000"; +})(); \ No newline at end of file diff --git a/Components/Backgrounds/Interactive-Hexagonal-Background/style.css b/Components/Backgrounds/Interactive-Hexagonal-Background/style.css new file mode 100644 index 00000000..6ac5a55b --- /dev/null +++ b/Components/Backgrounds/Interactive-Hexagonal-Background/style.css @@ -0,0 +1,70 @@ +body { + position: relative; + width: 100%; + min-height: 100vh; +} + +section { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; +} + +#particles { + background: #000000; +} + +#hexagonGrid { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + overflow: hidden; +} +#hexagonGrid .row { + display: inline-flex; + margin-top: -32px; + margin-left: -50px; +} +#hexagonGrid .row:nth-child(even) { + margin-left: 2px; +} +#hexagonGrid .row .hexagon { + position: relative; + width: 100px; + height: 110px; + margin: 4px 2px; + clip-path: polygon(50% 0%, 100% 25%, 100% 75%, 50% 100%, 0% 75%, 0% 25%); +} +#hexagonGrid .row .hexagon::before { + content: ""; + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + background: #000000; + opacity: 0.95; + transition: 1s; +} +#hexagonGrid .row .hexagon::after { + content: ""; + position: absolute; + top: 4px; + right: 4px; + bottom: 4px; + left: 4px; + background: #141414; + clip-path: polygon(50% 0%, 100% 25%, 100% 75%, 50% 100%, 0% 75%, 0% 25%); +} +#hexagonGrid .row .hexagon:hover::before { + background: #8CFD0B; + opacity: 1; + transition: 0s; +} +#hexagonGrid .row .hexagon:hover::after { + background: #000000; +} \ No newline at end of file diff --git a/assets/html_files/backgrounds.html b/assets/html_files/backgrounds.html index ae69bf72..d605616c 100644 --- a/assets/html_files/backgrounds.html +++ b/assets/html_files/backgrounds.html @@ -447,6 +447,21 @@

Interactive Balls Background

+
+

Interactive Hexagonal Background

+
+ + + +
+
+ + + +
+