Aside from some basic transitions, i'm pretty much a novice when it comes to animations in css/JS. For a Project that starts next week, i have commited to a specific animation that i find somewhat challenging. Here's the Animation explained:
- There should be 10-30 Images that rotate/circulate around a Ring/circle.
- The Images should also randomly have a small offset away from the Ring, as to give a "scattered" effect
- The Images should be spread around the ring to "fill" it.
- The Images should have a "bounce" effect or similar
Image of what i'd hope to achieve:
What i've tried so far: I've been researching some JS Libraries for Animations. Those that stood out to me were animeJS (https://animejs.com/) and MoJS (https://mojs.github.io/). I've decided to test out AnimeJS.
Here is a CodePen: CodePen
const imgContainer = document.getElementById("imgContainer");
const svgContainer = document.getElementById("svgContainer");
const imgURL =
"https://images.unsplash.com/photo-1678833823181-ec16d450d8c1?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=774&q=80";
function generateCircleWithRandomSizes(index) {
const randomSize = generateRandomNumberBetween(450, 520);
return `<div class="svgWrapper">
<svg width="${randomSize}" height="${randomSize}" fill="none" stroke="none" id="svgContainer">
<path id="path${index + 1}" fill="none" d="
m ${(800 - randomSize) / 2}, ${800 - randomSize}
a 1,1 0 1,1 ${randomSize},0
a 1,1 0 1,1 -${randomSize},0
" />
</svg>
</div>`;
}
function generateRandomNumberBetween(min, max) {
return Math.floor(Math.random() * (max - min + 1) + min);
}
for (let i = 0; i < 30; i++) {
imgContainer.innerHTML += `<img class="image" id="img${i + 1}" src="${imgURL}" />`;
svgContainer.innerHTML += generateCircleWithRandomSizes(i);
let path = anime.path(`#path${i + 1}`);
anime({
targets: `#img${i + 1}`,
translateX: path("x"),
translateY: path("y"),
easing: "linear",
duration: 10000,
loop: true
});
}
Here's the approach i'm currently trying, but as the CodePen shows, i'm running into multiple issues. I'm generating as many Circles as i have images and want target 1 Image per Path. This approach would give me the scattered effect i'm trying to get. However, as you can see, it seems that animeJS only animates one of the Images, and that it seems to follow the path, but offset to the top left. I'm assuming this has something to do with my CSS and how i "center" SVG/Path, which ultimately shows another issue i have. I'm not quite sure how to dynamically generate theses rings and always center them.
I'm having a bit of a hard time to put my finger on how to best solve this. Am i using the best library for this use case? Do i even need a library? Should i got at it from a completely different angle?
I'd really love to get some help on this.