3

I have a Wordpress gallery site where images open up in a Bootstrap 5 Modal, which opens up a Bootstrap Carousel.

The images are loaded in a post loop with a php foreach loop, one per slide.

I am trying to add hover magnification to each image with a small circle using blowup.js.

I have the zoom function moving correctly with each slide, however only the first image tracks where the mouse is. Subsequent magnifications are stuck on the top left corner.

Here is my Function:

(function ($) {
    
    // Update blowup when slide changes
    $("#gallery-carousel").on('slide.bs.carousel', function (){
        $(".img-zoom").blowup("destroy");
    });

    $("#gallery-carousel").on('slid.bs.carousel', function (){
        $(".img-zoom").blowup()
    });
      
})(jQuery);
      

This is the code that the function targets within the Carousel:


<div class="carousel-item">

 <div class="position-relative carousel-img">
      <img class="img-fluid img-zoom" src="<?php echo $image_url; ?>" />                                
 </div>

</div>

This is the JQuery in the plugin that is meant to track the zoomed coordinates:

  // Mouse motion on image
    $element.mousemove(function (e) {

      // Lens position coordinates
      var lensX = e.pageX - $options.width / 2;
      var lensY = e.pageY - $options.height / 2;

      // Relative coordinates of image
      var relX = e.pageX - $(this).offset().left;
      var relY = e.pageY - $(this).offset().top;
     
      // Zoomed image coordinates 
      var zoomX = -Math.floor(relX / $element.width() * (NATIVE_IMG.width * $options.scale) - $options.width / 2);
      var zoomY = -Math.floor(relY / $element.height() * (NATIVE_IMG.height * $options.scale) - $options.height / 2);

      var backPos = zoomX + "px " + zoomY + "px";
      var backgroundSize = NATIVE_IMG.width * $options.scale + "px " + NATIVE_IMG.height * $options.scale + "px";

    })
SMae
  • 41
  • 4

1 Answers1

1

The key was changing the "Zoomed image coordinates" from '$(element)' to '$(this)'.

I also changed all 'var' to 'const'

Here is the final code that got it working...

     
/**
 * blowup.js
 * Paul Krishnamurthy 2016
 *
 * https://paulkr.com
 * paul@paulkr.com
 */

 (function ($) {
  $.fn.blowup = function (attributes) {

    const $element = this;

    // If the target element is not an image
    if (!$element.is("img")) {
      console.log("%c Blowup.js Error: " + "%cTarget element is not an image.",
        "background: #FCEBB6; color: #F07818; font-size: 17px; font-weight: bold;",
        "background: #FCEBB6; color: #F07818; font-size: 17px;");
      return;
    }

    // Default attributes
    const defaults = {
      round         : true,
      width         : 200,
      height        : 200,
      background    : "transparent",
      shadow        : "0 8px 17px 0 rgba(0, 0, 0, 0.2)",
      border        : "6px solid #FFF",
      cursor        : true,
      zIndex        : 999999,
      scale         : 1,
      customClasses : ""
    }

    // Update defaults with custom attributes
    const $options = $.extend(defaults, attributes);

    // Modify target image
    $element.on('dragstart', function (e) { e.preventDefault(); });
    $element.css("cursor", $options.cursor ? "crosshair" : "none");

    // Create magnification lens element
    const lens = document.createElement("div");
    lens.id = "BlowupLens";

    // Attach the element to the body
    $("body").append(lens);

    // Updates styles
    $blowupLens = $("#BlowupLens");

    $blowupLens.css({
      "position"          : "absolute",
      "display"           : "none",
      "pointer-events"    : "none",
      "zIndex"            : $options.zIndex,
      "width"             : $options.width,
      "height"            : $options.height,
      "border"            : $options.border,
      "background"        : $options.background,
      "border-radius"     : $options.round ? "50%" : "none",
      "box-shadow"        : $options.shadow,
      "background-repeat" : "no-repeat",
    });

    // Add custom CSS classes
    $blowupLens.addClass($options.customClasses);

    // Show magnification lens
    $element.mouseenter(function () {
      $blowupLens.css("display", "block");
    })

    // Mouse motion on image
    $element.mousemove(function (e) {

      // Constants
      const $IMAGE_URL    = $('.active').find('img').attr('src');
      const NATIVE_IMG    = new Image();
      NATIVE_IMG.src    = $('.active').find('img').attr('src');

      // Lens position coordinates
      const lensX = e.pageX - $options.width / 2;
      const lensY = e.pageY - $options.height / 2;

      // Relative coordinates of image
      const relX = e.pageX - $(this).offset().left;
      const relY = e.pageY - $(this).offset().top;

      // Zoomed image coordinates
      zoomX =-6 -Math.floor(relX / $(this).width() * (NATIVE_IMG.width * $options.scale) - $options.width / 2);
      zoomY =-6 -Math.floor(relY / $(this).height() * (NATIVE_IMG.height * $options.scale) - $options.height / 2);
  
      const backPos = zoomX + "px " + zoomY + "px";
      const backgroundSize = NATIVE_IMG.width * $options.scale + "px " + NATIVE_IMG.height * $options.scale + "px";

      // Apply styles to lens
      $blowupLens.css({
        left                  : lensX,
        top                   : lensY,
        "background-image"    : "url(" + encodeURI($IMAGE_URL) + ")",
        "background-size"     : backgroundSize,
        "background-position" : backPos
      });
    })

    // Hide magnification lens
    $element.mouseleave(function () {
      $blowupLens.css("display", "none");
    });
  }
    })(jQuery);
    


// Artwork Magnification 

(function ($) {

    $(".img-zoom").blowup()

})(jQuery);

SMae
  • 41
  • 4