Skip to content

Commit 2932a92

Browse files
committed
ACP2E-3198: [cloud] Two-finger zoom and move issue on the real mobile device
1 parent 148c3ea commit 2932a92

File tree

1 file changed

+119
-59
lines changed

1 file changed

+119
-59
lines changed

lib/web/magnifier/magnify.js

Lines changed: 119 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,6 @@ define([
3131
endX,
3232
transitionEnabled,
3333
transitionActive = false,
34-
tapFlag = 0,
3534
allowZoomOut = false,
3635
allowZoomIn = true;
3736

@@ -227,7 +226,7 @@ define([
227226
return left;
228227
}
229228

230-
function checkFullscreenImagePosition($image, dimentions, widthStep, heightStep) {
229+
function checkFullscreenImagePosition($image, dimensions, widthStep, heightStep) {
231230
var $imageContainer,
232231
containerWidth,
233232
containerHeight,
@@ -246,20 +245,21 @@ define([
246245
top = $image.position().top;
247246
left = $image.position().left;
248247
ratio = $image.width() / $image.height();
249-
dimentions.height = isNaN(dimentions.height) ? dimentions.width / ratio : dimentions.height;
250-
dimentions.width = isNaN(dimentions.width) ? dimentions.height * ratio : dimentions.width;
248+
dimensions.height = isNaN(dimensions.height) ? dimensions.width / ratio : dimensions.height;
249+
dimensions.width = isNaN(dimensions.width) ? dimensions.height * ratio : dimensions.width;
251250

252-
top = dimentions.height >= containerHeight ?
253-
getTopValue($image, top, heightStep, dimentions.height, containerHeight) : 0;
251+
top = dimensions.height >= containerHeight ?
252+
getTopValue($image, top, heightStep, dimensions.height, containerHeight) : 0;
254253

255-
left = dimentions.width >= containerWidth ?
256-
getLeftValue(left, widthStep, dimentions.width, containerWidth) : 0;
254+
left = dimensions.width >= containerWidth ?
255+
getLeftValue(left, widthStep, dimensions.width, containerWidth) : 0;
257256

258-
right = dragFlag && left < (containerWidth - dimentions.width) / 2 ? 0 : left;
257+
right = dragFlag && left < (containerWidth - dimensions.width) / 2 ? 0 : left;
259258
bottom = dragFlag ? 0 : top;
260259

261-
settings = $.extend(dimentions, {
260+
settings = $.extend(dimensions, {
262261
top: top,
262+
bottom: bottom,
263263
left: left,
264264
right: right
265265
});
@@ -309,7 +309,7 @@ define([
309309
widthResult,
310310
heightResult,
311311
ratio,
312-
dimentions = {};
312+
dimensions = {};
313313

314314
if (allowZoomIn && (!transitionEnabled || !transitionActive) && (isTouchEnabled ||
315315
!$(zoomInButtonSelector).hasClass(zoomInDisabled))) {
@@ -352,18 +352,18 @@ define([
352352
}
353353

354354
if (imageWidth >= imageHeight && imageWidth !== imgOriginalSize.rw) {
355-
dimentions = $.extend(dimentions, {
355+
dimensions = $.extend(dimensions, {
356356
width: widthResult,
357357
height: 'auto'
358358
});
359-
checkFullscreenImagePosition($image, dimentions, -zoomWidthStep, -zoomHeightStep);
359+
checkFullscreenImagePosition($image, dimensions, -zoomWidthStep, -zoomHeightStep);
360360

361361
} else if (imageWidth < imageHeight && imageHeight !== imgOriginalSize.rh) {
362-
dimentions = $.extend(dimentions, {
362+
dimensions = $.extend(dimensions, {
363363
width: 'auto',
364364
height: heightResult
365365
});
366-
checkFullscreenImagePosition($image, dimentions, -zoomWidthStep, -zoomHeightStep);
366+
checkFullscreenImagePosition($image, dimensions, -zoomWidthStep, -zoomHeightStep);
367367
}
368368
}
369369

@@ -374,7 +374,7 @@ define([
374374
var $image,
375375
widthResult,
376376
heightResult,
377-
dimentions,
377+
dimensions,
378378
parentWidth,
379379
parentHeight,
380380
imageWidth,
@@ -414,7 +414,7 @@ define([
414414
zoomWidthStep = imageWidth - widthResult;
415415
heightResult = widthResult / ratio;
416416
zoomHeightStep = imageHeight - heightResult;
417-
dimentions = {
417+
dimensions = {
418418
width: widthResult,
419419
height: 'auto'
420420
};
@@ -423,44 +423,44 @@ define([
423423
zoomHeightStep = imageHeight - heightResult;
424424
widthResult = heightResult * ratio;
425425
zoomWidthStep = imageWidth - widthResult;
426-
dimentions = {
426+
dimensions = {
427427
width: 'auto',
428428
height: heightResult
429429
};
430430
}
431-
checkFullscreenImagePosition($image, dimentions, zoomWidthStep, zoomHeightStep);
431+
checkFullscreenImagePosition($image, dimensions, zoomWidthStep, zoomHeightStep);
432432
};
433433

434434
if (imageWidth >= imageHeight) {
435435
if (widthResult > parentWidth) {
436-
dimentions = {
436+
dimensions = {
437437
width: widthResult,
438438
height: 'auto'
439439
};
440-
checkFullscreenImagePosition($image, dimentions, zoomWidthStep, zoomHeightStep);
440+
checkFullscreenImagePosition($image, dimensions, zoomWidthStep, zoomHeightStep);
441441
} else if (heightResult > parentHeight) {
442-
dimentions = {
442+
dimensions = {
443443
width: widthResult,
444444
height: 'auto'
445445
};
446-
checkFullscreenImagePosition($image, dimentions, zoomWidthStep, zoomHeightStep);
446+
checkFullscreenImagePosition($image, dimensions, zoomWidthStep, zoomHeightStep);
447447
} else {
448448
allowZoomOut = dragFlag = false;
449449
toggleStandartNavigation();
450450
fitIntoParent();
451451
}
452452
} else if (heightResult > parentHeight) {
453-
dimentions = {
453+
dimensions = {
454454
width: 'auto',
455455
height: heightResult
456456
};
457-
checkFullscreenImagePosition($image, dimentions, zoomWidthStep, zoomHeightStep);
457+
checkFullscreenImagePosition($image, dimensions, zoomWidthStep, zoomHeightStep);
458458
} else if (widthResult > parentWidth) {
459-
dimentions = {
459+
dimensions = {
460460
width: 'auto',
461461
height: heightResult
462462
};
463-
checkFullscreenImagePosition($image, dimentions, zoomWidthStep, zoomHeightStep);
463+
checkFullscreenImagePosition($image, dimensions, zoomWidthStep, zoomHeightStep);
464464
} else {
465465
allowZoomOut = dragFlag = false;
466466
toggleStandartNavigation();
@@ -520,7 +520,6 @@ define([
520520
* Method which makes draggable picture. Also work on touch devices.
521521
*/
522522
function magnifierFullscreen(fotorama) {
523-
tapFlag = 0;
524523
var isDragActive = false,
525524
startX,
526525
startY,
@@ -532,7 +531,8 @@ define([
532531
$image = $(fullscreenImageSelector, $gallery),
533532
$imageContainer = $('[data-gallery-role="stage-shaft"] [data-active="true"]'),
534533
gallery = $gallery.data('fotorama'),
535-
pinchDimention;
534+
evCache = [],
535+
prevDiff = -1;
536536

537537
swipeSlide = _.throttle(function (direction) {
538538
$(gallerySelector).data('fotorama').show(direction);
@@ -556,7 +556,6 @@ define([
556556
swipeCondition = $image.width() / 10 + 20;
557557

558558
dragFlag = true;
559-
560559
if ($image.offset().left === $imageContainer.offset().left + $imageContainer.width() - $image.width() && e.keyCode === 39 ||
561560
endX - 1 < $imageContainer.offset().left + $imageContainer.width() - $image.width() && dx < 0 &&
562561
_.isNumber(endX) &&
@@ -609,6 +608,54 @@ define([
609608
}
610609
}
611610

611+
function pointerDownHandler(ev) {
612+
evCache.push(ev);
613+
}
614+
615+
function pointerMoveHandler(ev) {
616+
for (let i = 0; i < evCache.length; i++) {
617+
if (ev.pointerId === evCache[i].pointerId) {
618+
evCache[i] = ev;
619+
break;
620+
}
621+
}
622+
623+
if (evCache.length === 2) {
624+
let curDiff = Math.sqrt(
625+
Math.pow(evCache[1].clientX - evCache[0].clientX, 2) +
626+
Math.pow(evCache[1].clientY - evCache[0].clientY, 2)
627+
);
628+
629+
if (prevDiff > 0) {
630+
if (curDiff > prevDiff && allowZoomIn) {
631+
zoomIn(ev, 1.5 * curDiff, 1.5 * curDiff);
632+
}
633+
if (curDiff < prevDiff && allowZoomOut) {
634+
zoomOut(ev, 1.5 * curDiff, 1.5 * curDiff);
635+
}
636+
}
637+
638+
prevDiff = curDiff;
639+
}
640+
}
641+
642+
function pointerUpHandler(ev) {
643+
removeEvent(ev);
644+
645+
if (evCache.length < 2) {
646+
prevDiff = -1;
647+
}
648+
}
649+
650+
function removeEvent(ev) {
651+
for (let i = 0; i < evCache.length; i++) {
652+
if (evCache[i].pointerId === ev.pointerId) {
653+
evCache.splice(i, 1);
654+
break;
655+
}
656+
}
657+
}
658+
612659
/**
613660
* Sets image size to original or fit in parent block
614661
* @param e - event object
@@ -625,29 +672,58 @@ define([
625672
}
626673

627674
proportions = imgOriginalSize.rw / imgOriginalSize.rh;
628-
629675
if (allowZoomIn) {
630676
zoomIn(e, imgOriginalSize.rw - $image.width(), imgOriginalSize.rh - $image.height());
631-
} else if (proportions > $imageContainer.width() / $imageContainer.height()) {
632-
zoomOut(e, imgOriginalSize.rw - $imageContainer.width(), imgOriginalSize.rw / proportions);
633-
} else {
677+
} else if (allowZoomOut) {
634678
zoomOut(e, imgOriginalSize.rw * proportions, imgOriginalSize.rh - $imageContainer.height());
635679
}
636680
}
637681

638-
function detectDoubleTap(e) {
639-
let now = new Date().getTime(),
640-
timesince = now - tapFlag;
682+
function detectDoubleTap() {
683+
let lastTap = 0;
684+
let timeout;
641685

642-
if (timesince > 20 && (isTouchEnabled && timesince < 400) || (!isTouchEnabled && timesince < 2000)) {
643-
transitionActive = false;
644-
dblClickHandler(e);
645-
}
646-
tapFlag = now;
686+
return function doubleTap(event) {
687+
const curTime = new Date().getTime();
688+
const tapLen = curTime - lastTap;
689+
690+
if (tapLen < 500 && tapLen > 50) {
691+
event.preventDefault();
692+
693+
transitionActive = false;
694+
dblClickHandler(event);
695+
prevDiff = -1;
696+
} else {
697+
timeout = setTimeout(() => {
698+
clearTimeout(timeout);
699+
}, 500);
700+
}
701+
702+
lastTap = curTime;
703+
};
647704
}
648705

649706
if (isTouchEnabled) {
650-
$image.on('touchend', detectDoubleTap);
707+
$image.off('pointerdown');
708+
$image.on('pointerdown', pointerDownHandler);
709+
710+
$image.off('pointermove');
711+
$image.on('pointermove', pointerMoveHandler);
712+
713+
$image.off('pointerup');
714+
$image.on('pointerup', pointerUpHandler);
715+
716+
$image.off('pointercancel');
717+
$image.on('pointercancel', pointerUpHandler);
718+
719+
$image.off('pointerout');
720+
$image.on('pointerout', pointerUpHandler);
721+
722+
$image.off('pointerleave');
723+
$image.on('pointerleave', pointerUpHandler);
724+
725+
$image.off('touchend');
726+
$image.on('touchend', detectDoubleTap());
651727
} else {
652728
$image.off('dblclick');
653729
$image.on('dblclick', dblClickHandler);
@@ -657,17 +733,10 @@ define([
657733
toggleZoomButtons($image, isTouchEnabled, checkForVideo(fotorama.activeFrame.$stageFrame));
658734
}
659735

660-
function getDimention(event) {
661-
return Math.sqrt(
662-
(event.touches[0].clientX - event.touches[1].clientX) * (event.touches[0].clientX - event.touches[1].clientX) +
663-
(event.touches[0].clientY - event.touches[1].clientY) * (event.touches[0].clientY - event.touches[1].clientY));
664-
}
665-
666736
$image.off(isTouchEnabled ? 'touchstart' : 'pointerdown mousedown MSPointerDown');
667737
$image.on(isTouchEnabled ? 'touchstart' : 'pointerdown mousedown MSPointerDown', function (e) {
668738
if (e && e.originalEvent.touches && e.originalEvent.touches.length >= 2) {
669739
e.preventDefault();
670-
pinchDimention = getDimention(e.originalEvent);
671740
isDragActive = false;
672741

673742
if ($image.hasClass(imageDraggableClass)) {
@@ -696,19 +765,10 @@ define([
696765
$image.on(isTouchEnabled ? 'touchmove' : 'mousemove pointermove MSPointerMove', function (e) {
697766
if (e && e.originalEvent.touches && e.originalEvent.touches.length >= 2) {
698767
e.preventDefault();
699-
var currentDimention = getDimention(e.originalEvent);
700768

701769
if ($image.hasClass(imageDraggableClass)) {
702770
$image.removeClass(imageDraggableClass);
703771
}
704-
705-
if (currentDimention < pinchDimention) {
706-
zoomOut(e);
707-
pinchDimention = currentDimention;
708-
} else if (currentDimention > pinchDimention) {
709-
zoomIn(e);
710-
pinchDimention = currentDimention;
711-
}
712772
} else {
713773
var clientX,
714774
clientY;

0 commit comments

Comments
 (0)