不用递归制作滑块
给定以下 jsFiddle,如何在不构建堆栈的情况下实现与我所做的相同的效果?
我尝试做这样的事情:
jQuery(document).ready(function () {
'use strict';
(function ($) {
function validateOptions(options) {
if (typeof(options.delay) == typeof(0)) {
$.error('Delay value must an integer.');
return false;
} else if (options.delay < 0) {
$.error('Delay value must be greater than zero.');
return false;
}
if (typeof(options.direction) == typeof('')) {
$.error('Direction value must be a string.');
return false;
} else if (!(options.direction in ['left', 'right', 'up', 'down'])) {
$.error('Direction value must be "left", "right", "up", or "down".');
return false;
}
if (typeof(options.easing) == typeof('')) {
$.error('Easing value must be a string.');
return false;
}
if (typeof(options.selector) == typeof('')) {
$.error('Selector value must be a string.');
return false;
}
if (options.transition < 0) {
$.error('Transition value must be greater than zero.');
return false;
}
return true;
}
var methods = {
init: function (options) {
return this.each(function () {
var settings = {
delay: 5000,
direction: 'left',
easing: 'swing',
selector: '*',
transition: 3000
};
if (options) {
$.extend(settings, options);
}
$(this).css({
overflow: 'hidden',
position: 'relative'
});
var styles = {
left: 0,
position: 'absolute',
top: 0
};
switch (settings.direction) {
case 'left':
styles.left = $(this).width() + 'px';
break;
case 'right':
styles.left = -$(this).width() + 'px';
break;
case 'up':
styles.top = $(this).height() + 'px';
break;
case 'down':
styles.top = -$(this).height() + 'px';
break;
default:
jQuery.error('Direction ' + settings.direction + ' is not valid for jQuery.fn.cycle');
break;
}
$(this).children(settings.selector).css(styles).first().css({
left: 0,
top: 0
});
if ($(this).children(settings.selector).length > 1) {
$(this).cycle('slide', settings);
}
});
},
slide: function (options) {
return this.each(function () {
var settings = {
delay: 5000,
direction: 'left',
easing: 'swing',
selector: '*',
transition: 3000
}, animation, property, value;
if (options) {
$.extend(settings, options);
}
switch (settings.direction) {
case 'left':
animation = {left: '-=' + $(this).width()};
property = 'left';
value = $(this).width();
break;
case 'right':
animation = {left: '+=' + $(this).width()};
property = 'left';
value = -$(this).width();
break;
case 'up':
animation = {top: '-=' + $(this).height()};
property = 'top';
value = $(this).height();
break;
case 'down':
animation = {top: '+=' + $(this).height()};
property = 'top';
value = -$(this).height();
break;
default:
jQuery.error('Direction ' + settings.direction + ' is not valid for jQuery.fn.cycle');
break;
}
$(this).children(settings.selector + ':first-child').each(function () {
$(this).delay(settings.delay);
$(this).animate(
animation,
settings.transition,
settings.easing,
function () {
$(this).css(property, value);
}
);
});
$(this).append($(this).children(settings.selector + ':first-child').detach());
$(this).children(settings.selector + ':first-child').each(function () {
$(this).delay(settings.delay);
$(this).animate(
animation,
settings.transition,
settings.easing,
function () {
$(this).parent().cycle('slide', settings);
}
);
});
});
}
};
jQuery.fn.cycle = function (method, options) {
if (methods[method]) {
return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));
} else if (typeof method === 'object' || !method) {
return methods.init.apply(this, arguments);
} else {
$.error('Method ' + method + ' does not exist on jQuery.fn.cycle');
}
};
}(jQuery));
jQuery('.slider').cycle();
});
但是 < code>each() 方法不考虑循环期间添加的节点。
Given the following jsFiddle, how can I implement the same effect as I have made without building on the stack?
I tried doing something like this:
jQuery(document).ready(function () {
'use strict';
(function ($) {
function validateOptions(options) {
if (typeof(options.delay) == typeof(0)) {
$.error('Delay value must an integer.');
return false;
} else if (options.delay < 0) {
$.error('Delay value must be greater than zero.');
return false;
}
if (typeof(options.direction) == typeof('')) {
$.error('Direction value must be a string.');
return false;
} else if (!(options.direction in ['left', 'right', 'up', 'down'])) {
$.error('Direction value must be "left", "right", "up", or "down".');
return false;
}
if (typeof(options.easing) == typeof('')) {
$.error('Easing value must be a string.');
return false;
}
if (typeof(options.selector) == typeof('')) {
$.error('Selector value must be a string.');
return false;
}
if (options.transition < 0) {
$.error('Transition value must be greater than zero.');
return false;
}
return true;
}
var methods = {
init: function (options) {
return this.each(function () {
var settings = {
delay: 5000,
direction: 'left',
easing: 'swing',
selector: '*',
transition: 3000
};
if (options) {
$.extend(settings, options);
}
$(this).css({
overflow: 'hidden',
position: 'relative'
});
var styles = {
left: 0,
position: 'absolute',
top: 0
};
switch (settings.direction) {
case 'left':
styles.left = $(this).width() + 'px';
break;
case 'right':
styles.left = -$(this).width() + 'px';
break;
case 'up':
styles.top = $(this).height() + 'px';
break;
case 'down':
styles.top = -$(this).height() + 'px';
break;
default:
jQuery.error('Direction ' + settings.direction + ' is not valid for jQuery.fn.cycle');
break;
}
$(this).children(settings.selector).css(styles).first().css({
left: 0,
top: 0
});
if ($(this).children(settings.selector).length > 1) {
$(this).cycle('slide', settings);
}
});
},
slide: function (options) {
return this.each(function () {
var settings = {
delay: 5000,
direction: 'left',
easing: 'swing',
selector: '*',
transition: 3000
}, animation, property, value;
if (options) {
$.extend(settings, options);
}
switch (settings.direction) {
case 'left':
animation = {left: '-=' + $(this).width()};
property = 'left';
value = $(this).width();
break;
case 'right':
animation = {left: '+=' + $(this).width()};
property = 'left';
value = -$(this).width();
break;
case 'up':
animation = {top: '-=' + $(this).height()};
property = 'top';
value = $(this).height();
break;
case 'down':
animation = {top: '+=' + $(this).height()};
property = 'top';
value = -$(this).height();
break;
default:
jQuery.error('Direction ' + settings.direction + ' is not valid for jQuery.fn.cycle');
break;
}
$(this).children(settings.selector + ':first-child').each(function () {
$(this).delay(settings.delay);
$(this).animate(
animation,
settings.transition,
settings.easing,
function () {
$(this).css(property, value);
}
);
});
$(this).append($(this).children(settings.selector + ':first-child').detach());
$(this).children(settings.selector + ':first-child').each(function () {
$(this).delay(settings.delay);
$(this).animate(
animation,
settings.transition,
settings.easing,
function () {
$(this).parent().cycle('slide', settings);
}
);
});
});
}
};
jQuery.fn.cycle = function (method, options) {
if (methods[method]) {
return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));
} else if (typeof method === 'object' || !method) {
return methods.init.apply(this, arguments);
} else {
$.error('Method ' + method + ' does not exist on jQuery.fn.cycle');
}
};
}(jQuery));
jQuery('.slider').cycle();
});
But the each()
method does not take into account nodes that are added during the loop.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您可以通过
setInterval()
启动您的_cycle()
函数,以定期更新滑块:请注意,我重命名了您原来的
_cycle()
函数到_cycle2()
,并删除了delay_duration
参数。您可以在此处查看工作演示。You can launch your
_cycle()
function throughsetInterval()
, to periodically update the slider:Note that I renamed your original
_cycle()
function to_cycle2()
, and removed thedelay_duration
parameter. You can see a working demo here.你不想要类似 while(true) 的东西。
您的问题源于这样一个事实:您正在创建一个静态函数,然后尝试弄清楚如何在将其全部保留在静态函数范围内的约束下为子级设置动画。
相反,您应该为每个元素创建一个对象的实例,让该对象维护滑块的状态,并让它通过滑块操作所需的实现来更新该状态。
http://jsfiddle.net/qjVJF/3/
You don't want anything resembling while(true).
Your problem stems from the fact that you're creating a static function and then trying to figure out how to animate the children with the constraint of keeping it all in scope of your static function.
You should instead create an instance of an object per element, let the object maintain the state of the slider and have it update that state via an implementation necessary for the slider to operate.
http://jsfiddle.net/qjVJF/3/
也许这个插件 http://docs.jquery.com/Plugins/livequery 可以帮助你?
Maybe this plugin http://docs.jquery.com/Plugins/livequery can help you?