Please go to lib\web\magnifier\magnifier.js and replace it by the following code:
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
(function ($) {
$.fn.magnify = function (options) {
'use strict';
var magnify = new Magnify($(this), options);
/*events must be tracked here*/
/**
* Return that from _init function
*
*/
return magnify;
};
function Magnify(element, options) {
var gOptions = options || {},
$box = $(element),
$thumb,
that = this,
largeWrapper = options.largeWrapper || '.magnifier-preview',
$largeWrapper = $(largeWrapper);
curThumb = null,
currentOpts = {
x: 0,
y: 0,
w: 0,
h: 0,
lensW: 0,
lensH: 0,
lensBgX: 0,
lensBgY: 0,
largeW: 0,
largeH: 0,
largeL: 0,
largeT: 0,
zoom: 2,
zoomMin: 1.1,
zoomMax: 5,
mode: 'outside',
eventType: 'click',
status: 0,
zoomAttached: false,
zoomable: gOptions.zoomable !== undefined ?
gOptions.zoomable
: false,
onthumbenter: gOptions.onthumbenter !== undefined ?
gOptions.onthumbenter
: null,
onthumbmove: gOptions.onthumbmove !== undefined ?
gOptions.onthumbmove
: null,
onthumbleave: gOptions.onthumbleave !== undefined ?
gOptions.onthumbleave
: null,
onzoom: gOptions.onzoom !== undefined ?
gOptions.onzoom
: null
},
pos = {
t: 0,
l: 0,
x: 0,
y: 0
},
gId = 0,
status = 0,
curIdx = '',
curLens = null,
curLarge = null,
lensbg = gOptions.bg !== undefined ? gOptions.lensbg : true,
gZoom = gOptions.zoom !== undefined ?
gOptions.zoom
: currentOpts.zoom,
gZoomMin = gOptions.zoomMin !== undefined ?
gOptions.zoomMin
: currentOpts.zoomMin,
gZoomMax = gOptions.zoomMax !== undefined ?
gOptions.zoomMax
: currentOpts.zoomMax,
gMode = gOptions.mode || currentOpts.mode,
gEventType = gOptions.eventType || currentOpts.eventType,
data = {},
inBounds = false,
isOverThumb = false,
rate = 1,
paddingX = 0,
paddingY = 0,
enabled = true,
showWrapper = true;
var MagnifyCls = {
magnifyHidden: 'magnify-hidden',
magnifyOpaque: 'magnify-opaque',
magnifyFull: 'magnify-fullimage'
};
/**
* Update Lens positon on.
*
*/
that.update = function () {
updateLensOnLoad();
};
/**
* Init new Magnifier
*
*/
that.init = function () {
_init($box, options);
};
function _toBoolean(str) {
if (typeof str === 'string') {
if (str === 'true') {
return true;
} else if (str === 'false' || '') {
return false;
}
console.warn('Wrong type: can\'t be transformed to Boolean');
} else if (typeof str === 'boolean') {
return str;
}
}
function createLens(thumb) {
if ($(thumb).siblings('.magnify-lens').length) {
return false;
}
var lens = $('
');
$(thumb).parent().append(lens);
}
function updateLensOnLoad(idx, thumb, large, largeWrapper) {
var lens = $box.find('.magnify-lens'),
textWrapper;
if (data[idx].status === 1) {
textWrapper = $('
');
lens.className = 'magnifier-loader magnify-hidden';
textWrapper.html('Loading...');
lens.html('').append(textWrapper);
} else if (data[idx].status === 2) {
lens.addClass(MagnifyCls.magnifyHidden);
lens.html('');
large.id = idx + '-large';
large.style.width = data[idx].largeW * rate + 'px';
large.style.height = data[idx].largeH + 'px';
large.className = 'magnifier-large magnify-hidden';
if (data[idx].mode === 'inside') {
lens.append(large);
} else {
largeWrapper.html('').append(large);
}
}
data[idx].lensH = data[idx].lensH > $thumb.height() ? $thumb.height() : data[idx].lensH;
if (Math.round(data[idx].lensW) === 0) {
lens.css('display', 'none');
} else {
lens.css({
width: data[idx].lensW + 1 + 'px',
height: data[idx].lensH - 1 + 'px',
display: ''
});
}
}
function getMousePos() {
var xPos = pos.x - currentOpts.x,
yPos = pos.y - currentOpts.y,
t,
l;
inBounds = xPos < 0 || yPos < 0 || xPos > currentOpts.w || yPos > currentOpts.h ? false : true;
l = xPos - currentOpts.lensW / 2;
t = yPos - currentOpts.lensH / 2;
if (currentOpts.mode !== 'inside') {
if (xPos < currentOpts.lensW / 2) {
l = 0;
}
if (yPos < currentOpts.lensH / 2) {
t = 0;
}
if (xPos - currentOpts.w + Math.ceil(currentOpts.lensW / 2) > 0) {
l = currentOpts.w - Math.ceil(currentOpts.lensW + 2);
}
if (yPos - currentOpts.h + Math.ceil(currentOpts.lensH / 2) > 0) {
t = currentOpts.h - Math.ceil(currentOpts.lensH);
}
pos.l = l;
pos.t = t;
currentOpts.lensBgX = pos.l;
currentOpts.lensBgY = pos.t;
if (currentOpts.mode === 'inside') {
currentOpts.largeL = xPos * (currentOpts.zoom - currentOpts.lensW / currentOpts.w);
currentOpts.largeT = yPos * (currentOpts.zoom - currentOpts.lensH / currentOpts.h);
} else {
currentOpts.largeL = currentOpts.lensBgX * currentOpts.zoom * (currentOpts.largeWrapperW / currentOpts.w) * rate;
currentOpts.largeT = currentOpts.lensBgY * currentOpts.zoom * (currentOpts.largeWrapperH / currentOpts.h);
}
}
}
function onThumbEnter() {
if (_toBoolean(enabled)) {
currentOpts = data[curIdx];
curLens = $box.find('.magnify-lens');
if (currentOpts.status === 2) {
curLens.removeClass(MagnifyCls.magnifyOpaque);
curLarge = $('#' + curIdx + '-large');
curLarge.removeClass(MagnifyCls.magnifyHidden);
} else if (currentOpts.status === 1) {
curLens.className = 'magnifier-loader';
}
}
}
function onThumbLeave() {
if (currentOpts.status > 0) {
var handler = currentOpts.onthumbleave;
if (handler !== null) {
handler({
thumb: curThumb,
lens: curLens,
large: curLarge,
x: pos.x,
y: pos.y
});
}
if (!curLens.hasClass(MagnifyCls.magnifyHidden)) {
curLens.addClass(MagnifyCls.magnifyHidden);
//$curThumb.removeClass(MagnifyCls.magnifyOpaque);
if (curLarge !== null) {
curLarge.addClass(MagnifyCls.magnifyHidden);
}
}
}
}
function move() {
if (_toBoolean(enabled)) {
if (status !== currentOpts.status) {
onThumbEnter();
}
if (currentOpts.status > 0) {
curThumb.className = currentOpts.thumbCssClass + ' magnify-opaque';
if (currentOpts.status === 1) {
curLens.className = 'magnifier-loader';
} else if (currentOpts.status === 2) {
curLens.removeClass(MagnifyCls.magnifyHidden);
curLarge.removeClass(MagnifyCls.magnifyHidden);
curLarge.css({
left: '-' + currentOpts.largeL + 'px',
top: '-' + currentOpts.largeT + 'px'
});
}
pos.t = pos.t <= 0 ? 0 : pos.t;
curLens.css({
left: pos.l + paddingX + 'px',
top: pos.t + 1 + paddingY + 'px'
});
if (lensbg) {
curLens.css({
'background-color': 'rgba(f,f,f,.5)'
});
} else {
curLens.get(0).style.backgroundPosition = '-' +
currentOpts.lensBgX + 'px -' +
currentOpts.lensBgY + 'px';
}
var handler = currentOpts.onthumbmove;
if (handler !== null) {
handler({
thumb: curThumb,
lens: curLens,
large: curLarge,
x: pos.x,
y: pos.y
});
}
}
status = currentOpts.status;
}
}
function setThumbData(thumb, thumbData) {
var thumbBounds = thumb.getBoundingClientRect(),
w = 0,
h = 0;
thumbData.x = thumbBounds.left;
thumbData.y = thumbBounds.top;
thumbData.w = thumbBounds.right - thumbData.x;
thumbData.h = thumbBounds.bottom - thumbData.y;
if (thumbData.mode === 'inside') {
w = thumbData.w;
h = thumbData.h;
} else {
w = thumbData.largeWrapperW;
h = thumbData.largeWrapperH;
}
thumbData.largeW = thumbData.zoom * w;
thumbData.largeH = thumbData.zoom * h;
thumbData.lensW = thumbData.w / thumbData.zoom / rate;
thumbData.lensH = thumbData.h / thumbData.zoom;
}
function _init($box, options) {
var opts = {};
if (options.thumb === undefined) {
return false;
}
$thumb = $box.find(options.thumb);
if ($thumb.length) {
for (var key in options) {
opts[key] = options[key];
}
opts.thumb = $thumb;
enabled = opts.enabled;
if (_toBoolean(enabled)) {
$largeWrapper.show().css('display', '');
$largeWrapper.addClass(MagnifyCls.magnifyHidden);
set(opts);
} else {
$largeWrapper.empty().hide();
}
}
return that;
}
function hoverEvents(thumb) {
$(thumb).on('mouseover', function (e) {
if (showWrapper) {
if (currentOpts.status !== 0) {
onThumbLeave();
}
handleEvents(e);
isOverThumb = inBounds;
}
}).trigger('mouseover');
}
function clickEvents(thumb) {
$(thumb).on('click', function (e) {
if (showWrapper) {
if (!isOverThumb) {
if (currentOpts.status !== 0) {
onThumbLeave();
}
handleEvents(e);
isOverThumb = true;
}
}
});
}
function bindEvents(eType, thumb) {
switch (eType) {
case 'hover':
hoverEvents(thumb);
break;
case 'click':
clickEvents(thumb);
break;
}
}
function handleEvents(e) {
var src = e.target;
curIdx = src.id;
curThumb = src;
onThumbEnter(src);
setThumbData(curThumb, currentOpts);
pos.x = e.clientX;
pos.y = e.clientY;
getMousePos();
move();
var handler = currentOpts.onthumbenter;
if (handler !== null) {
handler({
thumb: curThumb,
lens: curLens,
large: curLarge,
x: pos.x,
y: pos.y
});
}
}
function set(options) {
if (data[options.thumb.id] !== undefined) {
curThumb = options.thumb;
return false;
}
var thumbObj = new Image(),
largeObj = new Image(),
$thumb = options.thumb,
thumb = $thumb.get(0),
idx = thumb.id,
largeUrl,
largeWrapper = $(options.largeWrapper),
zoom = options.zoom || thumb.getAttribute('data-zoom') || gZoom,
zoomMin = options.zoomMin || gZoomMin,
zoomMax = options.zoomMax || gZoomMax,
mode = options.mode || thumb.getAttribute('data-mode') || gMode,
eventType = options.eventType || thumb.getAttribute('data-eventType') || gEventType,
onthumbenter = options.onthumbenter !== undefined ?
options.onthumbenter
: currentOpts.onthumbenter,
onthumbleave = options.onthumbleave !== undefined ?
options.onthumbleave
: currentOpts.onthumbleave,
onthumbmove = options.onthumbmove !== undefined ?
options.onthumbmove
: currentOpts.onthumbmove;
largeUrl = $thumb.data('original') || gOptions.full || $thumb.attr('src');
if (thumb.id === '') {
idx = thumb.id = 'magnifier-item-' + gId;
gId += 1;
}
createLens(thumb, idx);
if (options.width) {
largeWrapper.width(options.width);
}
if (options.height) {
largeWrapper.height(options.height);
}
if (options.top) {
if (typeof options.top == 'function') {
var top = options.top() + 'px';
} else {
var top = options.top + 'px';
}
if (largeWrapper.length) {
largeWrapper[0].style.top = top.replace('%px', '%');
}
}
if (options.left) {
if (typeof options.left == 'function') {
var left = options.left() + 'px';
} else {
var left = options.left + 'px';
}
if (largeWrapper.length) {
largeWrapper[0].style.left = left.replace('%px', '%');
}
}
data[idx] = {
zoom: zoom,
zoomMin: zoomMin,
zoomMax: zoomMax,
mode: mode,
eventType: eventType,
thumbCssClass: thumb.className,
zoomAttached: false,
status: 0,
largeUrl: largeUrl,
largeWrapperId: mode === 'outside' ? largeWrapper.attr('id') : null,
largeWrapperW: mode === 'outside' ? largeWrapper.width() : null,
largeWrapperH: mode === 'outside' ? largeWrapper.height() : null,
onthumbenter: onthumbenter,
onthumbleave: onthumbleave,
onthumbmove: onthumbmove
};
rate = $thumb.width() / $thumb.height() / (data[idx].largeWrapperW / data[idx].largeWrapperH);
paddingX = ($thumb.parent().width() - $thumb.width()) / 2;
paddingY = ($thumb.parent().height() - $thumb.height()) / 2;
showWrapper = false;
$(thumbObj).on('load', function () {
data[idx].status = 1;
$(largeObj).on('load', function () {
if (largeObj.width > largeWrapper.width() || largeObj.height > largeWrapper.height()) {
showWrapper = true;
bindEvents(eventType, thumb);
data[idx].status = 2;
data[idx].zoom = largeObj.height / largeWrapper.height();
setThumbData(thumb, data[idx]);
updateLensOnLoad(idx, thumb, largeObj, largeWrapper);
}
});
largeObj.src = data[idx].largeUrl;
});
thumbObj.src = thumb.src;
}
function onMousemove(e) {
pos.x = e.clientX;
pos.y = e.clientY;
getMousePos();
if (gEventType === 'hover') {
isOverThumb = inBounds;
}
if (inBounds && isOverThumb) {
$largeWrapper.removeClass(MagnifyCls.magnifyHidden);
move();
} else {
onThumbLeave();
isOverThumb = false;
$largeWrapper.addClass(MagnifyCls.magnifyHidden);
}
}
function onScroll() {
if (curThumb !== null) {
setThumbData(curThumb, currentOpts);
}
}
function onMouseLeave(e) {
onThumbLeave();
isOverThumb = false;
$largeWrapper.addClass(MagnifyCls.magnifyHidden);
}
$(window).on('scroll', onScroll);
$(window).resize(function () {
_init($box, gOptions);
});
$box.on('mousemove', onMousemove);
$box.on('mouseleave', onMouseLeave);
_init($box, gOptions);
}
}(jQuery));
You can view and download these code here
Once you finished, please try to run SSH command:
php bin/magento setup:upgrade
php bin/magento setup:static-content:deploy -f
php bin/magento cache:flush
Check out for Magento 2 Extensions right now, They are cool and awesome!
Thanks for reading!