UnstableFractal
UnstableFractal

Reputation: 1422

jQuery, next, prev, cycling to first and last

Sorry for this confusing title. What i'm trying to do is a function (or just a simple way), which will do simple .next(), but if there's no next element, match first. And the same for .prev() - if there's no previous element, match last. So i made it this way:

var current_selected = getSelected();
if(current_selected.length) {
    var prev = current_selected.prev();
    if(prev.length) {
        setSelected(prev);
        return;
    }
}
setSelected(getLast());

But i don't really like it, i think there's some pretty way do it. Any thoughts? (getSelected and getLast returns jQuery objects.

Upvotes: 0

Views: 1960

Answers (4)

jmar777
jmar777

Reputation: 39649

You could create some little convenience plugins:

$.fn.nextWrap = function() {
    var $next = this.next();
    if ($next.length) return $next;
    return this.siblings().first();
};

$.fn.prevWrap = function() {
    var $prev = this.prev();
    if ($prev.length) return $prev;
    return this.siblings().last();
};

Then you can simply do $('#something').nextWrap() or $('#something').prevWrap().

Here's a quick demo: http://jsfiddle.net/qpDKL/

Note: This will behave mostly like prev() and next() (with the wrap behavior, of course), but it doesn't support the prev|next(selector) syntax.


Edit: Here's a slightly more terse plugin syntax since they're nearly the same anyway:

$.each(['next', 'prev'], function(i, nextOrPrev) {
    $.fn[nextOrPrev + 'Wrap'] = function() {
        var $item = this[nextOrPrev]();
        if ($item.length) return $item;
        return this.siblings()[nextOrPrev === 'next' ? 'first' : 'last']();
    };
});

Upvotes: 6

emerson.marini
emerson.marini

Reputation: 9348

Something around these lines:

if (!$('selected').next().length)
    return $('selected').parent().children().first();
else
    return $('selected').next();

if (!$('selected').prev().length)
    return $('selected').parent().children().last();
else
    return $('selected').prev();

Upvotes: 0

Explosion Pills
Explosion Pills

Reputation: 191729

The best way that I can think of would be to have an array of the elements that you want to cycle. You can cycle through an array in two ways:

array.push(array.shift());

or

var count = 0;
function cycle() {
    return array[count++ % array.length];
}

I think the former looks cleaner.

http://jsfiddle.net/ExplosionPIlls/feeF5/

Upvotes: 0

Arun P Johny
Arun P Johny

Reputation: 388316

This will work for prev case

var current_selected = getSelected();

var prev = current_selected.prev();
if(prev.length) {
    setSelected(prev);
} else {
    setSelected(getLast());
}

Upvotes: 1

Related Questions