为Zepto添加Slide动画效果

一.缘由

公司的移动端项目,采用zepto为主要框架,但是zepto毕竟是精简版的jquery,体积小了,功能自然没有这么强大,特别是动画和选择器这两块,需要我们自己去拓展。

在项目开发过程中,很多页面过渡需要用到动画,简单的show/hide过渡太生硬,对用户不友好,并且移动端大多都是采用slide效果,此文主要是为zepto拓展slide动画。

二.发现

从zepto的在线文档上可以发现一个发布在github上的动画模块,但是缺少slide效果,度娘上找了找,相关的极少,只发现了一个slideDown的例子,所以我们就照着这个例子写了几个常用的slide动画。

三.行动

首先,我们把动画方向分为上下滑动和左右滑动,滑动形式分为元素自身的伸缩和相对位移

1.左右slide

这应该是最常用的一个效果

贴上代码:注释部分二选一, slideLeft 和 slideRight 的滑动形式必须设为一致,不然无法工作

$.fn.slideLeft = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘hidden‘
});
//获取元素宽度
var width = this.width();

//-------通过伸缩元素宽度实现动画-------
//return this.css({
// top: 0,
// position: position,
// visibility: ‘visible‘,
// overflow: ‘auto‘
//}).animate({ width: 0 }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
top: 0,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘
}).animate({ left: -width }, speed, null, callback);
};

$.fn.slideRight = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘hidden‘
});
//获取元素宽度
var width = this.width() === 0 ? $(window).width() : this.width();

//-------通过伸缩元素宽度实现动画-------
//return this.css({
// top: 0,
// width: 0,
// position: position,
// visibility: ‘visible‘,
// overflow: ‘auto‘
//}).animate({ width: width }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
top: 0,
left: -width,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘,
}).animate({ left: 0 }, speed, null, callback);
};

$.fn.slideLeft = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘hidden‘
            });
            //获取元素宽度
            var width = this.width();

            //-------通过伸缩元素宽度实现动画-------
            //return this.css({
            //    top: 0,
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘auto‘
            //}).animate({ width: 0 }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                top: 0,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘
            }).animate({ left: -width }, speed, null, callback);
        };

        $.fn.slideRight = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘hidden‘
            });
            //获取元素宽度
            var width = this.width() === 0 ? $(window).width() : this.width();

            //-------通过伸缩元素宽度实现动画-------
            //return this.css({
            //    top: 0,
            //    width: 0,
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘auto‘
            //}).animate({ width: width }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                top: 0,
                left: -width,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘,
            }).animate({ left: 0 }, speed, null, callback);
        };

左右位移效果图:

左右伸缩效果图:

2.上下slide

贴上代码:注释部分二选一, slideUp 和 slideDown 的滑动形式必须设为一致,不然无法工作

$.fn.slideDown = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘hidden‘
});
//获取元素高度
var height = this.height() === 0 ? $(window).height() : this.height();

//-------通过伸缩元素高度实现动画-------
//return this.css({
// position: position,
// visibility: ‘visible‘,
// overflow: ‘auto‘,
// height: 0
//}).animate({ height: height }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
top: -height,
left: 0,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘
}).animate({ top: 0 }, speed, null, callback);
};

$.fn.slideUp = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘auto‘
});
//获取元素高度
var height = this.height();

//-------通过伸缩元素高度实现动画-------
//return this.css({
// position: position,
// visibility: ‘visible‘,
// overflow: ‘hidden‘,
// height: height
//}).animate({ height: 0 }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
left: 0,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘
}).animate({ top: -height }, speed, null, callback);
};

 $.fn.slideDown = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘hidden‘
            });
            //获取元素高度
            var height = this.height() === 0 ? $(window).height() : this.height();

            //-------通过伸缩元素高度实现动画-------
            //return this.css({
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘auto‘,
            //    height: 0
            //}).animate({ height: height }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                top: -height,
                left: 0,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘
            }).animate({ top: 0 }, speed, null, callback);
        };

        $.fn.slideUp = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘auto‘
            });
            //获取元素高度
            var height = this.height();

            //-------通过伸缩元素高度实现动画-------
            //return this.css({
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘hidden‘,
            //    height: height
            //}).animate({ height: 0 }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                left: 0,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘
            }).animate({ top: -height }, speed, null, callback);
        };

上下位移效果图:

上下伸缩效果图:

四.结束

这样,我们在项目中就能愉快的使用动画了。

顺便附上整个动画模块,但在这之前必须先添加上animate模块,因为zepto本身是不具有animate事件的,许多模块都是单独分出去的,可以参考这里,代码我们可以从github中的animate模块复制进去。

//animate模块
; (function ($, undefined) {
var prefix = ‘‘, eventPrefix,
vendors = { Webkit: ‘webkit‘, Moz: ‘‘, O: ‘o‘ },
testEl = document.createElement(‘div‘),
supportedTransforms = /^((translate|rotate|scale)(X|Y|Z|3d)?|matrix(3d)?|perspective|skew(X|Y)?)$/i,
transform,
transitionProperty, transitionDuration, transitionTiming, transitionDelay,
animationName, animationDuration, animationTiming, animationDelay,
cssReset = {}

function dasherize(str) { return str.replace(/([A-Z])/g, ‘-$1‘).toLowerCase() }
function normalizeEvent(name) { return eventPrefix ? eventPrefix + name : name.toLowerCase() }

if (testEl.style.transform === undefined) $.each(vendors, function (vendor, event) {
if (testEl.style[vendor + ‘TransitionProperty‘] !== undefined) {
prefix = ‘-‘ + vendor.toLowerCase() + ‘-‘
eventPrefix = event
return false
}
})

transform = prefix + ‘transform‘
cssReset[transitionProperty = prefix + ‘transition-property‘] =
cssReset[transitionDuration = prefix + ‘transition-duration‘] =
cssReset[transitionDelay = prefix + ‘transition-delay‘] =
cssReset[transitionTiming = prefix + ‘transition-timing-function‘] =
cssReset[animationName = prefix + ‘animation-name‘] =
cssReset[animationDuration = prefix + ‘animation-duration‘] =
cssReset[animationDelay = prefix + ‘animation-delay‘] =
cssReset[animationTiming = prefix + ‘animation-timing-function‘] = ‘‘

$.fx = {
off: (eventPrefix === undefined && testEl.style.transitionProperty === undefined),
speeds: { _default: 400, fast: 200, slow: 600 },
cssPrefix: prefix,
transitionEnd: normalizeEvent(‘TransitionEnd‘),
animationEnd: normalizeEvent(‘AnimationEnd‘)
}

$.fn.animate = function (properties, duration, ease, callback, delay) {
if ($.isFunction(duration))
callback = duration, ease = undefined, duration = undefined
if ($.isFunction(ease))
callback = ease, ease = undefined
if ($.isPlainObject(duration))
ease = duration.easing, callback = duration.complete, delay = duration.delay, duration = duration.duration
if (duration) duration = (typeof duration == ‘number‘ ? duration :
($.fx.speeds[duration] || $.fx.speeds._default)) / 1000
if (delay) delay = parseFloat(delay) / 1000
return this.anim(properties, duration, ease, callback, delay)
}

$.fn.anim = function (properties, duration, ease, callback, delay) {
var key, cssValues = {}, cssProperties, transforms = ‘‘,
that = this, wrappedCallback, endEvent = $.fx.transitionEnd,
fired = false

if (duration === undefined) duration = $.fx.speeds._default / 1000
if (delay === undefined) delay = 0
if ($.fx.off) duration = 0

if (typeof properties == ‘string‘) {
// keyframe animation
cssValues[animationName] = properties
cssValues[animationDuration] = duration + ‘s‘
cssValues[animationDelay] = delay + ‘s‘
cssValues[animationTiming] = (ease || ‘linear‘)
endEvent = $.fx.animationEnd
} else {
cssProperties = []
// CSS transitions
for (key in properties)
if (supportedTransforms.test(key)) transforms += key + ‘(‘ + properties[key] + ‘) ‘
else cssValues[key] = properties[key], cssProperties.push(dasherize(key))

if (transforms) cssValues[transform] = transforms, cssProperties.push(transform)
if (duration > 0 && typeof properties === ‘object‘) {
cssValues[transitionProperty] = cssProperties.join(‘, ‘)
cssValues[transitionDuration] = duration + ‘s‘
cssValues[transitionDelay] = delay + ‘s‘
cssValues[transitionTiming] = (ease || ‘linear‘)
}
}

wrappedCallback = function (event) {
if (typeof event !== ‘undefined‘) {
if (event.target !== event.currentTarget) return // makes sure the event didn‘t bubble from "below"
$(event.target).unbind(endEvent, wrappedCallback)
} else
$(this).unbind(endEvent, wrappedCallback) // triggered by setTimeout

fired = true
$(this).css(cssReset)
callback && callback.call(this)
}
if (duration > 0) {
this.bind(endEvent, wrappedCallback)
// transitionEnd is not always firing on older Android phones
// so make sure it gets fired
setTimeout(function () {
if (fired) return
wrappedCallback.call(that)
}, ((duration + delay) * 1000) + 25)
}

// trigger page reflow so new elements can animate
this.size() && this.get(0).clientLeft

this.css(cssValues)

if (duration <= 0) setTimeout(function () {
that.each(function () { wrappedCallback.call(this) })
}, 0)

return this
}

testEl = null
})(Zepto)
//动画效果模块
; (function ($, undefined) {
var document = window.document, docElem = document.documentElement,
origShow = $.fn.show, origHide = $.fn.hide, origToggle = $.fn.toggle

function anim(el, speed, opacity, scale, callback) {
if (typeof speed == ‘function‘ && !callback) callback = speed, speed = undefined
var props = { opacity: opacity }
if (scale) {
props.scale = scale
el.css($.fx.cssPrefix + ‘transform-origin‘, ‘0 0‘)
}
return el.animate(props, speed, null, callback);
}

function hide(el, speed, scale, callback) {
return anim(el, speed, 0, scale, function () {
origHide.call($(this))
callback && callback.call(this)
})
}

$.fn.show = function (speed, callback) {
origShow.call(this)
//不是很理解作者的想法,如果这里继续执行下去,所有调用zepto原生show事件的元素,都会被这个事件覆盖,并且透明度都为被设为1...
if (speed === undefined) return origShow.call(this) // 原版为:if (speed === undefined) speed = 0
else this.css(‘opacity‘, 0)
return anim(this, speed, 1, ‘1,1‘, callback)
}

$.fn.hide = function (speed, callback) {
if (speed === undefined) return origHide.call(this)
else return hide(this, speed, ‘0,0‘, callback)
}

$.fn.toggle = function (speed, callback) {
if (speed === undefined || typeof speed == ‘boolean‘)
return origToggle.call(this, speed)
else return this.each(function () {
var el = $(this)
el[el.css(‘display‘) == ‘none‘ ? ‘show‘ : ‘hide‘](speed, callback)
})
}

$.fn.fadeTo = function (speed, opacity, callback) {
return anim(this, speed, opacity, null, callback)
}

$.fn.fadeIn = function (speed, callback) {
var target = this.css(‘opacity‘)
if (target > 0) this.css(‘opacity‘, 0)
else target = 1
return origShow.call(this).fadeTo(speed, target, callback)
}

$.fn.fadeOut = function (speed, callback) {
return hide(this, speed, null, callback)
}

$.fn.fadeToggle = function (speed, callback) {
return this.each(function () {
var el = $(this)
el[
(el.css(‘opacity‘) == 0 || el.css(‘display‘) == ‘none‘) ? ‘fadeIn‘ : ‘fadeOut‘
](speed, callback)
})
}

$.fn.slideDown = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘hidden‘
});
//获取元素高度
var height = this.height() === 0 ? $(window).height() : this.height();

//-------通过伸缩元素高度实现动画-------
//return this.css({
// position: position,
// visibility: ‘visible‘,
// overflow: ‘auto‘,
// height: 0
//}).animate({ height: height }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
top: -height,
left: 0,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘
}).animate({ top: 0 }, speed, null, callback);
};

$.fn.slideUp = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘auto‘
});
//获取元素高度
var height = this.height();

//-------通过伸缩元素高度实现动画-------
//return this.css({
// position: position,
// visibility: ‘visible‘,
// overflow: ‘hidden‘,
// height: height
//}).animate({ height: 0 }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
left: 0,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘
}).animate({ top: -height }, speed, null, callback);
};

$.fn.slideLeft = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘hidden‘
});
//获取元素宽度
var width = this.width();

//-------通过伸缩元素宽度实现动画-------
//return this.css({
// top: 0,
// position: position,
// visibility: ‘visible‘,
// overflow: ‘auto‘
//}).animate({ width: 0 }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
top: 0,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘
}).animate({ left: -width }, speed, null, callback);
};

$.fn.slideRight = function (speed, callback) {
//获取元素position
var position = this.css(‘position‘);
this.show().css({
position: ‘absolute‘,
visibility: ‘hidden‘
});
//获取元素宽度
var width = this.width() === 0 ? $(window).width() : this.width();

//-------通过伸缩元素宽度实现动画-------
//return this.css({
// top: 0,
// width: 0,
// position: position,
// visibility: ‘visible‘,
// overflow: ‘auto‘
//}).animate({ width: width }, speed, null, callback);

//-------通过移动元素相对位置实现动画-------
return this.css({
top: 0,
left: -width,
position: position,
visibility: ‘visible‘,
overflow: ‘auto‘,
}).animate({ left: 0 }, speed, null, callback);
};
})(Zepto)

 //animate模块
    ; (function ($, undefined) {
        var prefix = ‘‘, eventPrefix,
          vendors = { Webkit: ‘webkit‘, Moz: ‘‘, O: ‘o‘ },
          testEl = document.createElement(‘div‘),
          supportedTransforms = /^((translate|rotate|scale)(X|Y|Z|3d)?|matrix(3d)?|perspective|skew(X|Y)?)$/i,
          transform,
          transitionProperty, transitionDuration, transitionTiming, transitionDelay,
          animationName, animationDuration, animationTiming, animationDelay,
          cssReset = {}

        function dasherize(str) { return str.replace(/([A-Z])/g, ‘-$1‘).toLowerCase() }
        function normalizeEvent(name) { return eventPrefix ? eventPrefix + name : name.toLowerCase() }

        if (testEl.style.transform === undefined) $.each(vendors, function (vendor, event) {
            if (testEl.style[vendor + ‘TransitionProperty‘] !== undefined) {
                prefix = ‘-‘ + vendor.toLowerCase() + ‘-‘
                eventPrefix = event
                return false
            }
        })

        transform = prefix + ‘transform‘
        cssReset[transitionProperty = prefix + ‘transition-property‘] =
        cssReset[transitionDuration = prefix + ‘transition-duration‘] =
        cssReset[transitionDelay = prefix + ‘transition-delay‘] =
        cssReset[transitionTiming = prefix + ‘transition-timing-function‘] =
        cssReset[animationName = prefix + ‘animation-name‘] =
        cssReset[animationDuration = prefix + ‘animation-duration‘] =
        cssReset[animationDelay = prefix + ‘animation-delay‘] =
        cssReset[animationTiming = prefix + ‘animation-timing-function‘] = ‘‘

        $.fx = {
            off: (eventPrefix === undefined && testEl.style.transitionProperty === undefined),
            speeds: { _default: 400, fast: 200, slow: 600 },
            cssPrefix: prefix,
            transitionEnd: normalizeEvent(‘TransitionEnd‘),
            animationEnd: normalizeEvent(‘AnimationEnd‘)
        }

        $.fn.animate = function (properties, duration, ease, callback, delay) {
            if ($.isFunction(duration))
                callback = duration, ease = undefined, duration = undefined
            if ($.isFunction(ease))
                callback = ease, ease = undefined
            if ($.isPlainObject(duration))
                ease = duration.easing, callback = duration.complete, delay = duration.delay, duration = duration.duration
            if (duration) duration = (typeof duration == ‘number‘ ? duration :
                            ($.fx.speeds[duration] || $.fx.speeds._default)) / 1000
            if (delay) delay = parseFloat(delay) / 1000
            return this.anim(properties, duration, ease, callback, delay)
        }

        $.fn.anim = function (properties, duration, ease, callback, delay) {
            var key, cssValues = {}, cssProperties, transforms = ‘‘,
                that = this, wrappedCallback, endEvent = $.fx.transitionEnd,
                fired = false

            if (duration === undefined) duration = $.fx.speeds._default / 1000
            if (delay === undefined) delay = 0
            if ($.fx.off) duration = 0

            if (typeof properties == ‘string‘) {
                // keyframe animation
                cssValues[animationName] = properties
                cssValues[animationDuration] = duration + ‘s‘
                cssValues[animationDelay] = delay + ‘s‘
                cssValues[animationTiming] = (ease || ‘linear‘)
                endEvent = $.fx.animationEnd
            } else {
                cssProperties = []
                // CSS transitions
                for (key in properties)
                    if (supportedTransforms.test(key)) transforms += key + ‘(‘ + properties[key] + ‘) ‘
                    else cssValues[key] = properties[key], cssProperties.push(dasherize(key))

                if (transforms) cssValues[transform] = transforms, cssProperties.push(transform)
                if (duration > 0 && typeof properties === ‘object‘) {
                    cssValues[transitionProperty] = cssProperties.join(‘, ‘)
                    cssValues[transitionDuration] = duration + ‘s‘
                    cssValues[transitionDelay] = delay + ‘s‘
                    cssValues[transitionTiming] = (ease || ‘linear‘)
                }
            }

            wrappedCallback = function (event) {
                if (typeof event !== ‘undefined‘) {
                    if (event.target !== event.currentTarget) return // makes sure the event didn‘t bubble from "below"
                    $(event.target).unbind(endEvent, wrappedCallback)
                } else
                    $(this).unbind(endEvent, wrappedCallback) // triggered by setTimeout

                fired = true
                $(this).css(cssReset)
                callback && callback.call(this)
            }
            if (duration > 0) {
                this.bind(endEvent, wrappedCallback)
                // transitionEnd is not always firing on older Android phones
                // so make sure it gets fired
                setTimeout(function () {
                    if (fired) return
                    wrappedCallback.call(that)
                }, ((duration + delay) * 1000) + 25)
            }

            // trigger page reflow so new elements can animate
            this.size() && this.get(0).clientLeft

            this.css(cssValues)

            if (duration <= 0) setTimeout(function () {
                that.each(function () { wrappedCallback.call(this) })
            }, 0)

            return this
        }

        testEl = null
    })(Zepto)
    //动画效果模块
    ; (function ($, undefined) {
        var document = window.document, docElem = document.documentElement,
          origShow = $.fn.show, origHide = $.fn.hide, origToggle = $.fn.toggle

        function anim(el, speed, opacity, scale, callback) {
            if (typeof speed == ‘function‘ && !callback) callback = speed, speed = undefined
            var props = { opacity: opacity }
            if (scale) {
                props.scale = scale
                el.css($.fx.cssPrefix + ‘transform-origin‘, ‘0 0‘)
            }
            return el.animate(props, speed, null, callback);
        }

        function hide(el, speed, scale, callback) {
            return anim(el, speed, 0, scale, function () {
                origHide.call($(this))
                callback && callback.call(this)
            })
        }

        $.fn.show = function (speed, callback) {
            origShow.call(this)
            //不是很理解作者的想法,如果这里继续执行下去,所有调用zepto原生show事件的元素,都会被这个事件覆盖,并且透明度都为被设为1...
            if (speed === undefined) return origShow.call(this) // 原版为:if (speed === undefined) speed = 0
            else this.css(‘opacity‘, 0)
            return anim(this, speed, 1, ‘1,1‘, callback)
        }

        $.fn.hide = function (speed, callback) {
            if (speed === undefined) return origHide.call(this)
            else return hide(this, speed, ‘0,0‘, callback)
        }

        $.fn.toggle = function (speed, callback) {
            if (speed === undefined || typeof speed == ‘boolean‘)
                return origToggle.call(this, speed)
            else return this.each(function () {
                var el = $(this)
                el[el.css(‘display‘) == ‘none‘ ? ‘show‘ : ‘hide‘](speed, callback)
            })
        }

        $.fn.fadeTo = function (speed, opacity, callback) {
            return anim(this, speed, opacity, null, callback)
        }

        $.fn.fadeIn = function (speed, callback) {
            var target = this.css(‘opacity‘)
            if (target > 0) this.css(‘opacity‘, 0)
            else target = 1
            return origShow.call(this).fadeTo(speed, target, callback)
        }

        $.fn.fadeOut = function (speed, callback) {
            return hide(this, speed, null, callback)
        }

        $.fn.fadeToggle = function (speed, callback) {
            return this.each(function () {
                var el = $(this)
                el[
                  (el.css(‘opacity‘) == 0 || el.css(‘display‘) == ‘none‘) ? ‘fadeIn‘ : ‘fadeOut‘
                ](speed, callback)
            })
        }

        $.fn.slideDown = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘hidden‘
            });
            //获取元素高度
            var height = this.height() === 0 ? $(window).height() : this.height();

            //-------通过伸缩元素高度实现动画-------
            //return this.css({
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘auto‘,
            //    height: 0
            //}).animate({ height: height }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                top: -height,
                left: 0,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘
            }).animate({ top: 0 }, speed, null, callback);
        };

        $.fn.slideUp = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘auto‘
            });
            //获取元素高度
            var height = this.height();

            //-------通过伸缩元素高度实现动画-------
            //return this.css({
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘hidden‘,
            //    height: height
            //}).animate({ height: 0 }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                left: 0,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘
            }).animate({ top: -height }, speed, null, callback);
        };

        $.fn.slideLeft = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘hidden‘
            });
            //获取元素宽度
            var width = this.width();

            //-------通过伸缩元素宽度实现动画-------
            //return this.css({
            //    top: 0,
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘auto‘
            //}).animate({ width: 0 }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                top: 0,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘
            }).animate({ left: -width }, speed, null, callback);
        };

        $.fn.slideRight = function (speed, callback) {
            //获取元素position
            var position = this.css(‘position‘);
            this.show().css({
                position: ‘absolute‘,
                visibility: ‘hidden‘
            });
            //获取元素宽度
            var width = this.width() === 0 ? $(window).width() : this.width();

            //-------通过伸缩元素宽度实现动画-------
            //return this.css({
            //    top: 0,
            //    width: 0,
            //    position: position,
            //    visibility: ‘visible‘,
            //    overflow: ‘auto‘
            //}).animate({ width: width }, speed, null, callback);

            //-------通过移动元素相对位置实现动画-------
            return this.css({
                top: 0,
                left: -width,
                position: position,
                visibility: ‘visible‘,
                overflow: ‘auto‘,
            }).animate({ left: 0 }, speed, null, callback);
        };
    })(Zepto)
时间: 2024-11-17 11:19:40

为Zepto添加Slide动画效果的相关文章

自己动手丰衣足食,为Zepto添加Slide动画效果

一.缘由 公司的移动端项目,采用zepto为主要框架,但是zepto毕竟是精简版的jquery,体积小了,功能自然没有这么强大,特别是动画和选择器这两块,需要我们自己去拓展. 在项目开发过程中,很多页面过渡需要用到动画,简单的show/hide过渡太生硬,对用户不友好,并且移动端大多都是采用slide效果,此文主要是为zepto拓展slide动画. 二.发现 从zepto的在线文档上可以发现一个发布在github上的动画模块,但是缺少slide效果,度娘上找了找,相关的极少,只发现了一个slid

UITableView添加波浪动画效果

- (void)reloadDataAnimateWithWave:(WaveAnimation)animation; { [self setContentOffset:self.contentOffset animated:NO]; [UIView animateWithDuration:.2 animations:^{ [self setHidden:YES]; [self reloadData]; } completion:^(BOOL finished) { //Do something

想给UIVIew上控件添加一些动画效果

如果你还不知道怎样让一张图片缓缓滑动,渐渐消失,或者是在原地翻滚,不知道怎样让一个窗口弹出的时候有一点抖动的效果不那么僵硬,那正好,今儿在下总结的内容可能刚好能帮你实现你想要的效果(⊙o⊙)哦. 首先说一下什么是动画效果,动画效果有哪些好处吧: 这里所说的动画绝对不是你在电视上看到的,有剧情的那种(当然这句可能是废话),而是为了增加用户的体验感,通过对控件的属性或者layer进行一些处理达到美化界面的效果,主要是让界面看起来更加的生动,不会太枯燥.想象一下,你在用读书软件时候的翻页效果,就能被称

Jquery 动态交换两个div位置并添加Css动画效果

前端网页开发中我们经常会遇到需要动态置换两个DIV元素的位置,常见的思路大多是不考虑原始位置,直接采用append或者appendTo方式将两元素进行添加,该法未考虑原始位置,仅会添加为元素的最后一子元素. 今天将给大家介绍一种位置交换方式(判断兄弟元素是否存在),并添加简单的css效果. 设计思路 判断元素后边是否存在兄弟元素:存在则通过insertBefore方法将另一元素添加至其兄弟元素前,否则则直接采用appendTo方法添加至父元素. 核心代码 1.判断其后边是否存在兄弟元素 1 fu

贝塞尔曲线实现的购物车添加商品动画效果

效果图如下: 1.activity_main.xml <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/rly_bezier_curve_shopping_cart" android:layout_w

页面滚动--添加animation动画效果

<!DOCTYPE html><html><head> <meta charset="utf-8"/> <title>动画</title> <script src="jquery-1.7.2.min.js" type="text/javascript" charset="utf-8"></script> <!--<scr

ViewPager的动画效果(学习自慕课网)

先上效果一: 先上效果二: 先上效果三: 首先定义好viewPager控件,其次,是调用一行代码实现动画效果, pager.setPageTransformer(true,new DepthPageTransformer()); 前提是需要做一些准备操作的,且只有api3.0以上才可以有效. 注:因为属性动画是3.0以后才出现的,如果想在3.0以下的手机上实现动画,需要做一些更改,用nineoldandroids框架来代替属性动画.这里先不向下兼容了.如有想向下兼容的朋友,可以访问宏阳大神的博客

JavaScript网站设计实践(三)设计有特色的主页,给主页链接添加JavaScript动画脚本

原文:JavaScript网站设计实践(三)设计有特色的主页,给主页链接添加JavaScript动画脚本 一.主页一般都会比较有特色,现在在网站设计(二)实现的基础上,来给主页添加一点动画效果. 1.这里实现的动画效果是:当鼠标悬停在其中某个超链接时,会显示出属于该页面的背景缩略图,让用户知道这个链接的页面大概内容是什么. 效果图: 2.实现这个效果的思路 (1)把主页的几个链接的背景图片缩放到150px*150px,拼成一张750*150的图片,并保存为slideshow.png,存放到ima

Android animator Animation动画效果详解

Android的animation由四种类型组成 XML中 alpha 渐变透明度动画效果 scale 渐变尺寸伸缩动画效果 translate 画面转换位置移动动画效果 rotate 画面转移旋转动画效果 JavaCode中 AlphaAnimation 渐变透明度动画效果 ScaleAnimation 渐变尺寸伸缩动画效果 TranslateAnimation 画面转换位置移动动画效果 RotateAnimation 画面转移旋转动画效果 Android动画模式 Animation主要有两种