javascripthtmlcss-animations

Creating a JS circle animation from the cursor when someone clicks in a certain area


I am trying to make a section of my site that will allow users to click in it. When they click, an animation radiating from the tip of their cursor should appear signifying a click visually.

I have it working on only 1920 screen size, when I resize it even a single number down the hardcode breaks the circle no longer appears where I want it to.

So I am trying to find a better way of making this circle appear from the tip of the cursor whenever you click, it should work on any screensize without hardcoding.

I have tried adding a button in the test area and hardcoding the single location it will appear in after every click, I have tried to make the code in various formats but have not been able to get it to work.

HTML:

    <div class="testArea" id="blankBox">
      <div class="centered-text" id="clickText">Click here to start test</div>
    </div>

JS:

  function handleBlankBoxClick(event) {
    // If the countdown has ended, return early
    if (testDuration <= 0) {
      return;
    }

    if (!countdownStarted && testDuration > 0) {
      countdownStarted = true;
      startCountdown();
    }

    if (testDuration > 0) {
      clickText.style.display = "none"; // Hide the click text

      // Create a div element for the blue circle
      var circle = document.createElement("div");
      circle.classList.add("click-circle");
      blankBox.appendChild(circle);


      // Calculate the offset between the cursor position and the container position
      var rect = blankBox.getBoundingClientRect();
      var offsetX = event.clientX - 625;
      var offsetY = event.clientY - 335;
      
      // Set initial position of the circle to the cursor position
      circle.style.left = offsetX + "px";
      circle.style.top = offsetY + "px";

      // Add animation class to start the animation
      circle.classList.add("click-animation");

      // Remove the circle after animation completes
      setTimeout(function () {
        blankBox.removeChild(circle);
      }, 500); // Adjust this time according to your animation duration
    }
  }

CSS:

/* CSS for the click circle animation */
.click-circle {
  position: absolute;
  width: 150px;
  height: 150px;
  background-color: #8a26fc;
  border-radius: 50%;
  pointer-events: none; /* Ensure the circle doesn't interfere with clicks */
}

.click-animation {
  animation: click-effect 0.33s ease-out forwards; /* Decreased animation duration and added "forwards" to keep the final state */
}

@keyframes click-effect {
  0% {
    transform: scale(1);
    opacity: 0.7;
  }
  100% {
    transform: scale(3); /* Increased scale for larger circles */
    opacity: 0;
  }
}

Solution

  • I simplified this a bit, since you did not include a full working example.

    You can use pageX and pageY to get the absolute coordinates. I derived a value of 75 for the radius, based on the 150px CSS value.

    const handleClick = (event) => {
      const
        el = event.target,
        radius = 75,
        x = event.pageX - radius,
        y = event.pageY - radius,
        duration = 500;
      showClick(el, x, y, duration);
    };
    
    document.addEventListener('click', handleClick);
    
    const showClick = (el, x, y, duration) => {
      const circle = document.createElement('div');
      circle.classList.add('click-circle');
      el.appendChild(circle);
    
      // Set initial position of the circle to the cursor position
      Object.assign(circle.style, { left: `${x}px`, top: `${y}px` });
    
      // Add animation class to start the animation
      circle.classList.add('click-animation');
    
      // Remove the circle after animation completes
      setTimeout(function() {
        el.removeChild(circle);
      }, duration);
    };
    .click-circle {
      position: absolute;
      width: 150px;
      height: 150px;
      background-color: #8a26fc;
      border-radius: 50%;
      pointer-events: none;
      /* Ensure the circle doesn't interfere with clicks */
    }
    
    .click-animation {
      animation: click-effect 0.33s ease-out forwards;
      /* Decreased animation duration and added "forwards" to keep the final state */
    }
    
    @keyframes click-effect {
      0% {
        transform: scale(1);
        opacity: 0.7;
      }
      100% {
        transform: scale(3);
        /* Increased scale for larger circles */
        opacity: 0;
      }
    }