I am creating particle animation using Canvas & JavaScript. Currently, particles are generating from an emitter randomly & falling in a direction (top right corner to bottom left corner). collision detection effect is also working on mouse hover.
problem is:
I want to create separate color-wise multiple lines of particles (e.g:- blue colored particles should be in separate a line & red in a separate line).
how could I achieve this?

Sorry for bad drawing, any reference will be very useful. Thank you in advance.
(function() {
var requestAnimationFrame = window.requestAnimationFrame || window.mozRequestAnimationFrame || window.webkitRequestAnimationFrame || window.msRequestAnimationFrame ||
function(callback) {
window.setTimeout(callback, 1000 / 60);
};
window.requestAnimationFrame = requestAnimationFrame;
})();
var particleArr = [],
canvas = document.getElementById("canvas"),
ctx = canvas.getContext("2d"),
flakeCount = 700,
mouseX = -100,
mouseY = -100,
xMultiplier = 0.015
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
var rate = 0.07788656582264941;
function getRandomColor() {
// Random Color Generate
const colorArr = ["rgba(215,88,69, 1)", "rgba(117, 161, 199, 1)"]; // Blue & Orange Color
const randomColor = colorArr[Math.floor(Math.random() * colorArr.length)];
return randomColor;
}
function flow() {
ctx.clearRect(0, 0, canvas.width, canvas.height);
for (var i = 0; i < flakeCount; i++) {
var flake = particleArr[i],
x = mouseX,
y = mouseY,
minDist = 150,
x2 = flake.x,
y2 = flake.y;
var dist = Math.sqrt((x2 - x) * (x2 - x) + (y2 - y) * (y2 - y)),
dx = x2 - x,
dy = y2 - y;
if (dist < minDist) {
var force = minDist / (dist * dist),
xcomp = (x - x2) / dist,
ycomp = (y - y2) / dist,
deltaV = force / 2;
// deltaV = 0.03960597468566516
flake.velX -= deltaV * xcomp;
flake.velY -= deltaV * ycomp;
// flake.velX -= deltaV * xcomp + rate;
// flake.velY -= deltaV * ycomp + rate;
} else {
flake.velX *= .98;
if (flake.velY <= flake.speed) {
flake.velY = flake.speed
}
flake.velX += Math.cos(flake.step += .05) * flake.stepSize;
}
flake.y += flake.velY;
flake.x += flake.velX;
if (flake.y >= canvas.height || flake.y <= 0) {
reset(flake);
}
if (flake.x >= canvas.width || flake.x <= 0) {
reset(flake);
}
ctx.fillStyle = particleArr[i].color;
ctx.beginPath();
ctx.arc(flake.x, flake.y, flake.size, 0, Math.PI * 2);
ctx.fill();
}
requestAnimationFrame(flow);
// setTimeout(() => {
// requestAnimationFrame(flow);
// }, 1000 / 40);
};
function reset(flake) {
let temp = (Math.random() * 1) + 0.5;
flake.x = canvas.width;
flake.y = 50;
// flake.size = (Math.random() * 3) + 5;
flake.size = 6.692053245649504;
flake.speed = (Math.random() * 7) + 0.5;
flake.velY = flake.speed;
flake.velX = -xMultiplier * canvas.width * temp;
// flake.opacity = (Math.random() * 0.5) + 0.3;
}
function init() {
for (var i = 0; i < flakeCount; i++) {
var x = canvas.width,
y = 50,
size = 6.692053245649504,
speed = 0;
// size = (Math.random() * 3) + 5, // can change 3 to 4
// speed = (Math.random() * 1) + 0.5;
// opacity = (Math.random() * 0.5) + 0.3;
particleArr.push({
speed: speed,
velY: speed,
velX: -xMultiplier * canvas.width * speed,
x: x,
y: y,
size: size,
stepSize: (Math.random()) / 30,
step: 0,
angle: 360,
color: getRandomColor()
// opacity: opacity
});
}
requestAnimationFrame(flow);
// flow();
};
canvas.addEventListener("mousemove", function(e) {
mouseX = e.clientX,
mouseY = e.clientY
});
window.addEventListener( 'resize', onWindowResize, false );
function onWindowResize() {
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
}
init();
canvas{
background-color: #000000 !important;
}
body {
margin: 0;
overflow: hidden;
}`
<canvas id="canvas"></canvas>