TT35 Records
Dein Label für Indie, Punk, EDM & Subkultur.
*/
(function() {
var pJS = function(tag_id, params) {
var canvas_el = document.querySelector('#' + tag_id + ' > .particles-js-canvas-el');
// If not exists, create the canvas
if (!canvas_el) {
canvas_el = document.createElement('canvas');
canvas_el.className = 'particles-js-canvas-el';
canvas_el.style.width = '100%';
canvas_el.style.height = '100%';
document.getElementById(tag_id).appendChild(canvas_el);
}
this.pJS = {
canvas: {
el: canvas_el,
w: canvas_el.offsetWidth,
h: canvas_el.offsetHeight
},
particles: {
number: { value: 80 },
color: { value: '#ffffff' },
shape: { type: 'circle' },
opacity: { value: 0.5, random: true },
size: { value: 3, random: true },
line_linked: { enable: true, distance: 150, color: '#ffffff', opacity: 0.4, width: 1 },
move: { enable: true, speed: 1, direction: 'none', random: false, straight: false, out_mode: 'out', bounce: false, attract: { enable: false, rotateX: 600, rotateY: 1200 } },
array: []
},
interactivity: {
detect_on: 'canvas',
events: { onhover: { enable: true, mode: 'grab' }, onclick: { enable: true, mode: 'push' }, resize: true },
modes: { grab: { distance: 140, line_linked: { opacity: 1 } }, push: { particles_nb: 4 } }
},
fn: { interact: {}, modes: {}, vendors: {} },
retina_detect: true,
config_json: params
};
var p = this.pJS;
function launchParticles() {
p.fn.vendors.density_auto = function() {
p.particles.number.value = p.particles.number.value * (p.canvas.el.width * p.canvas.el.height / (600 * 600)) / 100;
};
p.fn.vendors.load_json = function(url) {
fetch(url).then(function(response) {
return response.json();
}).then(function(data) {
p.config_json = data;
p.fn.vendors.start();
}).catch(function(error) {
console.log('Error loading config file:', error);
});
};
p.fn.vendors.start = function() {
if (p.config_json.particles) {
Object.assign(p.particles, p.config_json.particles);
}
if (p.config_json.interactivity) {
Object.assign(p.interactivity, p.config_json.interactivity);
}
if (p.config_json.retina_detect) {
p.retina_detect = p.config_json.retina_detect;
}
p.canvas.context = p.canvas.el.getContext('2d');
p.retina_detect && window.devicePixelRatio > 1 ? p.canvas.pxratio = window.devicePixelRatio : p.canvas.pxratio = 1;
p.canvas.w = p.canvas.el.offsetWidth * p.canvas.pxratio;
p.canvas.h = p.canvas.el.offsetHeight * p.canvas.pxratio;
p.canvas.el.width = p.canvas.w;
p.canvas.el.height = p.canvas.h;
p.particles.color.value = '#ffffff'; // Override to always be white for this template
p.particles.line_linked.color = '#ffffff';
p.fn.vendors.density_auto();
p.fn.vendors.create_particles();
p.fn.vendors.draw();
p.interactivity.events.resize && window.addEventListener('resize', p.fn.vendors.canvas_size_set);
};
p.fn.vendors.canvas_size_set = function() {
p.canvas.w = p.canvas.el.offsetWidth * p.canvas.pxratio;
p.canvas.h = p.canvas.el.offsetHeight * p.canvas.pxratio;
p.canvas.el.width = p.canvas.w;
p.canvas.el.height = p.canvas.h;
p.interactivity.events.resize && p.fn.vendors.density_auto();
p.fn.vendors.create_particles();
};
p.fn.vendors.create_particles = function() {
p.particles.array = [];
for (var i = 0; i < p.particles.number.value; i++) {
p.particles.array.push(new p.fn.particle(p));
}
};
p.fn.vendors.draw = function() {
p.canvas.context.clearRect(0, 0, p.canvas.w, p.canvas.h);
p.particles.array.forEach(function(particle) {
particle.update(p.interactivity.modes);
});
requestAnimationFrame(p.fn.vendors.draw);
};
p.fn.particle = function(p) {
this.x = Math.random() * p.canvas.w;
this.y = Math.random() * p.canvas.h;
this.r = p.particles.size.value * p.canvas.pxratio;
this.opacity = p.particles.opacity.value;
this.color = p.particles.color.value;
this.vx = (Math.random() - 0.5) * p.particles.move.speed;
this.vy = (Math.random() - 0.5) * p.particles.move.speed;
this.draw = function() {
p.canvas.context.beginPath();
p.canvas.context.arc(this.x, this.y, this.r, 0, Math.PI * 2, false);
p.canvas.context.fillStyle = 'rgba(' + parseInt(this.color.substring(1,3),16) + ',' + parseInt(this.color.substring(3,5),16) + ',' + parseInt(this.color.substring(5,7),16) + ',' + this.opacity + ')';
p.canvas.context.fill();
p.canvas.context.closePath();
};
this.update = function(modes) {
// Move particles
this.x += this.vx;
this.y += this.vy;
// Bounce or out_mode
if (p.particles.move.out_mode === 'bounce') {
if (this.x + this.r > p.canvas.w || this.x - this.r < 0) this.vx = -this.vx;
if (this.y + this.r > p.canvas.h || this.y - this.r < 0) this.vy = -this.vy;
} else {
if (this.x - this.r > p.canvas.w) this.x = -this.r;
else if (this.x + this.r < 0) this.x = p.canvas.w + this.r;
if (this.y - this.r > p.canvas.h) this.y = -this.r;
else if (this.y + this.r < 0) this.y = p.canvas.h + this.r;
}
// Attract or repel based on interactivity
if (modes.grab && p.interactivity.events.onhover.mode === 'grab') {
var dx = p.interactivity.mouse.pos_x - this.x;
var dy = p.interactivity.mouse.pos_y - this.y;
var dist = Math.sqrt(dx * dx + dy * dy);
if (dist <= p.interactivity.modes.grab.distance) {
var ratio = 1 - (dist / p.interactivity.modes.grab.distance);
p.canvas.context.beginPath();
p.canvas.context.moveTo(this.x, this.y);
p.canvas.context.lineTo(p.interactivity.mouse.pos_x, p.interactivity.mouse.pos_y);
p.canvas.context.lineWidth = p.particles.line_linked.width;
p.canvas.context.strokeStyle = 'rgba(' + parseInt(p.particles.line_linked.color.substring(1,3),16) + ',' + parseInt(p.particles.line_linked.color.substring(3,5),16) + ',' + parseInt(p.particles.line_linked.color.substring(5,7),16) + ',' + (p.particles.line_linked.opacity * ratio) + ')';
p.canvas.context.stroke();
p.canvas.context.closePath();
}
}
this.draw();
};
};
p.interactivity.mouse = { pos_x: 0, pos_y: 0, click_pos_x: 0, click_pos_y: 0 };
canvas_el.addEventListener('mousemove', function(e) {
p.interactivity.mouse.pos_x = e.clientX;
p.interactivity.mouse.pos_y = e.clientY;
});
canvas_el.addEventListener('mouseleave', function() {
p.interactivity.mouse.pos_x = 0;
p.interactivity.mouse.pos_y = 0;
});
}
// Simplified default config matching template colors
var defaultParams = {
"particles": {
"number": { "value": 60, "density": { "enable": true, "value_area": 800 } },
"color": { "value": "#ffffff" },
"shape": { "type": "circle" },
"opacity": { "value": 0.4, "random": true, "anim": { "enable": false } },
"size": { "value": 4, "random": true, "anim": { "enable": false } },
"line_linked": { "enable": true, "distance": 150, "color": "#ffffff", "opacity": 0.3, "width": 1 },
"move": { "enable": true, "speed": 1, "direction": "none", "random": true, "straight": false, "out_mode": "out", "bounce": false, "attract": { "enable": false, "rotateX": 600, "rotateY": 1200 } }
},
"interactivity": {
"detect_on": "canvas",
"events": { "onhover": { "enable": true, "mode": "grab" }, "onclick": { "enable": true, "mode": "push" }, "resize": true },
"modes": { "grab": { "distance": 120, "line_linked": { "opacity": 0.8 } }, "push": { "particles_nb": 4 } }
},
"retina_detect": true
};
launchParticles(); // Start the simplified particles.js
};
window.particlesJS = function(tag_id, params) {
if(typeof params === 'object') {
return new pJS(tag_id, params);
}
};
// Initialize particles.js when the DOM is ready
particlesJS('particles-js', {});
})();