AngularJS1.x学习(仿微信图片手势缩放效果实现)

来源:互联网 发布:linux编辑器 编辑:程序博客网 时间:2024/09/21 09:02

这里写图片描述

最近,公司做一个混合应用项目,涉及到一个图片缩放功能,类似微信那样支持touch事件。

亲测,实现方案很不错,所以放出来,和大家分享一下,希望有人能用得到。

核心思想就是用到了CSS3的transform属性, 不多说,我们看代码:

'use strict';/** * @ngInject */module.exports = function () {    var _directive =  {        restrict : 'A',        scope    : false,        link     : _link    };    function _link(scope, element, attrs) {        var elWidth, elHeight;        // mode : 'pinch' or 'swipe'        var mode = '';        // distance between two touche points (mode : 'pinch')        var distance = 0;        var initialDistance = 0;        // image scaling        var scale = 1;        var relativeScale = 1;        var initialScale = 1;        var maxScale = parseInt(attrs.maxScale, 10);        if (isNaN(maxScale) || maxScale <= 1) {            maxScale = 3;        }        // position of the upper left corner of the element        var positionX = 0;        var positionY = 0;        var initialPositionX = 0;        var initialPositionY = 0;        // central origin (mode : 'pinch')        var originX = 0;        var originY = 0;        // start coordinate and amount of movement (mode : 'swipe')        var startX = 0;        var startY = 0;        var moveX = 0;        var moveY = 0;        var image = new Image();        image.onload = function() {            elWidth = element[0].clientWidth;            elHeight = element[0].clientHeight;            element.css({                '-webkit-transform-origin' : '0 0',                'transform-origin'         : '0 0'            });            element.on('touchstart', touchstartHandler);            element.on('touchmove', touchmoveHandler);            element.on('touchend', touchendHandler);        };        if (attrs.ngSrc) {            image.src = attrs.ngSrc;        } else {            image.src = attrs.src;        }        /**         * @param {object} evt         */        function touchstartHandler(evt) {            var touches = evt.originalEvent ? evt.originalEvent.touches : evt.touches;            startX = touches[0].clientX;            startY = touches[0].clientY;            initialPositionX = positionX;            initialPositionY = positionY;            moveX = 0;            moveY = 0;        }        /**         * @param {object} evt         */        function touchmoveHandler(evt) {            var touches = evt.originalEvent ? evt.originalEvent.touches : evt.touches;            if (mode === '') {                if (touches.length === 1 && scale > 1) {                    mode = 'swipe';                } else if (touches.length === 2) {                    mode = 'pinch';                    initialScale = scale;                    initialDistance = getDistance(touches);                    originX = touches[0].clientX -                        parseInt((touches[0].clientX - touches[1].clientX) / 2, 10) -                        element[0].offsetLeft - initialPositionX;                    originY = touches[0].clientY -                        parseInt((touches[0].clientY - touches[1].clientY) / 2, 10) -                        element[0].offsetTop - initialPositionY;                }            }            if (mode === 'swipe') {                evt.preventDefault();                moveX = touches[0].clientX - startX;                moveY = touches[0].clientY - startY;                positionX = initialPositionX + moveX;                positionY = initialPositionY + moveY;                transformElement();            } else if (mode === 'pinch') {                evt.preventDefault();                distance = getDistance(touches);                relativeScale = distance / initialDistance;                scale = relativeScale * initialScale;                positionX = originX * (1 - relativeScale) + initialPositionX + moveX;                positionY = originY * (1 - relativeScale) + initialPositionY + moveY;                transformElement();            }        }        /**         * @param {object} evt         */        function touchendHandler(evt) {            var touches = evt.originalEvent ? evt.originalEvent.touches : evt.touches;            if (mode === '' || touches.length > 0) {                return;            }            if (scale < 1) {                scale = 1;                positionX = 0;                positionY = 0;            } else if (scale > maxScale) {                scale = maxScale;                relativeScale = scale / initialScale;                positionX = originX * (1 - relativeScale) + initialPositionX + moveX;                positionY = originY * (1 - relativeScale) + initialPositionY + moveY;            } else {                if (positionX > 0) {                    positionX = 0;                } else if (positionX < elWidth * (1 - scale)) {                    positionX = elWidth * (1 - scale);                }                if (positionY > 0) {                    positionY = 0;                } else if (positionY < elHeight * (1 - scale)) {                    positionY = elHeight * (1 - scale);                }            }            transformElement(0.1);            mode = '';        }        /**         * @param {Array} touches         * @return {number}         */        function getDistance(touches) {            var d = Math.sqrt(Math.pow(touches[0].clientX - touches[1].clientX, 2) +                Math.pow(touches[0].clientY - touches[1].clientY, 2));            return parseInt(d, 10);        }        /**         * @param {number} [duration]         */        function transformElement(duration) {            var transition  = duration ? 'all cubic-bezier(0,0,.5,1) ' + duration + 's' : '';            var matrixArray = [scale, 0, 0, scale, positionX, positionY];            var matrix      = 'matrix(' + matrixArray.join(',') + ')';            element.css({                '-webkit-transition' : transition,                transition           : transition,                '-webkit-transform'  : matrix + ' translate3d(0,0,0)',                transform            : matrix            });        }    }    return _directive;};

上面代码中我们新建了一个directive,方便多个地方重用。

当我们建立好directive时候,该如何使用呢?

  <img style="width:100%;" src="assets/images/floorplan.jpeg" ng-pinch-zoom>

我们只需要在img文件上设定一个属性即可,是不是很简单呢?

3 0
原创粉丝点击