jquery call a function each time a class has changed - javascript

This is the markup for my navigation:
<div class="navigation navigation-fixed-top">
Home
About
</div>
And I have this jquery script, which is checking if href="#home" has class active to do something and if not to do something else.
This is the code:
var isActive = $('a[href="#home"]').hasClass('active');
$(".navigation")
.toggleClass("navigation-fixed-bottom", isActive)
.toggleClass("navigation-fixed-top", !isActive);
This is partially working because the class="active" is added automatically when I'm going the #about section or I'm clicking on it. It does this without refreshing the page so I need a way to to make this work without refreshing the page.
Any suggestions on how can I do this with jQuery/Javascript ?
UPDATE:
this is the name of the plugin Scrollit.js
THIS IS THE CODE RESPONSIBLE FOR ADDING THE ACTIVE CLASS ON THE NAVIGATION ELEMENTS:
(function($) {
'use strict';
var pluginName = 'ScrollIt',
pluginVersion = '1.0.3';
/*
* OPTIONS
*/
var defaults = {
upKey: 38,
downKey: 40,
easing: 'linear',
scrollTime: 600,
activeClass: 'active',
onPageChange: null,
topOffset : 0
};
$.scrollIt = function(options) {
/*
* DECLARATIONS
*/
var settings = $.extend(defaults, options),
active = 0,
lastIndex = $('[data-scroll-index]:last').attr('data-scroll-index');
/*
* METHODS
*/
/**
* navigate
*
* sets up navigation animation
*/
var navigate = function(ndx) {
if(ndx < 0 || ndx > lastIndex) return;
var targetTop = $('[data-scroll-index=' + ndx + ']').offset().top + settings.topOffset + 1;
$('html,body').animate({
scrollTop: targetTop,
easing: settings.easing
}, settings.scrollTime);
};
/**
* doScroll
*
* runs navigation() when criteria are met
*/
var doScroll = function (e) {
var target = $(e.target).closest("[data-scroll-nav]").attr('data-scroll-nav') ||
$(e.target).closest("[data-scroll-goto]").attr('data-scroll-goto');
navigate(parseInt(target));
};
/**
* keyNavigation
*
* sets up keyboard navigation behavior
*/
var keyNavigation = function (e) {
var key = e.which;
if(key == settings.upKey && active > 0) {
navigate(parseInt(active) - 1);
return false;
} else if(key == settings.downKey && active < lastIndex) {
navigate(parseInt(active) + 1);
return false;
}
return true;
};
/**
* updateActive
*
* sets the currently active item
*/
var updateActive = function(ndx) {
if(settings.onPageChange && ndx && (active != ndx)) settings.onPageChange(ndx);
active = ndx;
$('[data-scroll-nav]').removeClass(settings.activeClass);
$('[data-scroll-nav=' + ndx + ']').addClass(settings.activeClass);
};
/**
* watchActive
*
* watches currently active item and updates accordingly
*/
function navPosition() {
$('[data-scroll-nav]').toggleClass('navigation-fixed-bottom navigation-fixed-top');
}
var updateActive = function(ndx, navPosition) {
var watchActive = function() {
var winTop = $(window).scrollTop();
var visible = $('[data-scroll-index]').filter(function(ndx, div) {
return winTop >= $(div).offset().top + settings.topOffset &&
winTop < $(div).offset().top + (settings.topOffset) + $(div).outerHeight()
});
var newActive = visible.first().attr('data-scroll-index');
updateActive(newActive);
};
/*
* runs methods
*/
$(window).on('scroll',watchActive).on('scroll');
$(window).on('keydown', keyNavigation);
$('body').on('click','[data-scroll-nav], [data-scroll-goto]', function(e){
e.preventDefault();
doScroll(e);
});
};
}(jQuery));

$('[data-scroll-nav]').removeClass(settings.activeClass)
.toggleClass('navigation-fixed-bottom navigation-fixed-top');
and/or
$('[data-scroll-nav=' + ndx + ']').addClass(settings.activeClass)
.toggleClass('navigation-fixed-bottom navigation-fixed-top');
If you wanted to keep the original code cleaner, you could do a callback:
function myCallBackFunction() {
$('[data-scroll-nav]').toggleClass('navigation-fixed-bottom navigation-fixed-top');
}
var updateActive = function(ndx, myCallbackFunction) {..}

use jquery on to bind handlers to events you want to respond
$("a.active").on('click',function(){});

Related

Disable Tooltip in jQuery [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 2 years ago.
Improve this question
I have a little problem I'd like to solve.
https://byobcreatubolso.com/producto/sario-sart/
I have tooltip enabled inside my js code.
When the user clicks on the bag image, a thumbnail is displayed. I would like the samples to appear when the page loads without clicking on the bag image.
Any idea how to solve it? Thanks.
jQuery(document).ready(function() {
jQuery('.select-zone .seccion_imagen').css('cursor', 'pointer');
jQuery('.iconic-was-swatches__label').css('cursor', 'pointer');
jQuery('.js-toggle-next').css('cursor', 'pointer');
//First hide elements
jQuery('.variations .label label').hide();
jQuery('.variations .value').hide();
jQuery('.iconic-was-swatches__item').hide();
// Show first level
jQuery('.select-zone .seccion_imagen').on('click touchstart', function(event) {
jQuery('.select-zone .seccion_imagen').removeClass('selected');
jQuery(this).addClass('selected');
jQuery('.variations .value').hide('slow');
jQuery('.iconic-was-swatches__item').hide('slow');
var elemento = jQuery(this).attr('id');
jQuery('[for=' + elemento + ']').parent().next('.value').show('slow');
jQuery('[for=' + elemento + ']').parent().next('.value').children('ul').children('.iconic-was-swatches__label:first').nextUntil('.iconic-was-swatches__label').css('display', 'inline-block');
});
// Show second level
jQuery('.iconic-was-swatches__label').on('click touchstart', function(event) {
jQuery('.iconic-was-swatches__label').hide();
jQuery('.iconic-was-swatches__item').hide();
jQuery(this).nextUntil('.iconic-was-swatches__label').css('display', 'inline-block');
});
// Get selected values and draw in rigth place
jQuery(document).on('change', '.variations select', function() {
var selectID = jQuery(this).attr('id'),
selectedAttributte = jQuery(this).text(),
selectedValue = jQuery(this).val(),
CapitalValue = selectedValue.charAt(0).toUpperCase() + selectedValue.slice(1);
console.log('Select id ' + selectID);
console.log('Select attr ' + selectedAttributte);
console.log('Selected value ' + selectedValue);
jQuery('#js-selected-' + selectID).text(CapitalValue);
});
// Stamped text
jQuery('.js-toggle-next').on('click', function(event) {
jQuery(this).next('div').toggle('slow');
jQuery(this).next('div').next('label').next('input').val('');
});
jQuery('.stamped-text-input').on('keyup', function() {
if (!jQuery(this).val()) {
jQuery('#js-stamped-text-selected-container').addClass('d-none');
jQuery('#js-stamped-text-notice').addClass('d-none');
} else {
jQuery('#js-stamped-text-selected-container').removeClass('d-none');
jQuery('#js-stamped-text-notice').removeClass('d-none');
jQuery('#js-stamped-text-selected').text(jQuery(this).val());
jQuery('#js-stamped-text-sniffer').val(jQuery(this).val());
}
});
jQuery('[data-toggle="tooltip"]').tooltip()
// TO-DO move add to cart to rigth side
//jQuery('.single_variation_wrap').appendTo('#js-ad-to-cart');
// Move price variation
jQuery('.single_variation_wrap').on('change', function() {
if (jQuery('form.variations_form').length !== 0) {
var form = jQuery('form.variations_form'),
variable_product_price = '';
if (jQuery('.single_variation_wrap span.price span.amount').length !== 0) {
if (jQuery('#summary .entry-summary p.price span.amount').text() !== variable_product_price) {
variable_product_price = jQuery('.single_variation_wrap span.price span.amount').html();
jQuery('#summary .entry-summary p.price').html('');
jQuery('#summary .entry-summary p.price').html(variable_product_price);
}
}
}
});
});
/**
* jQuery 2.0+ REQUIRED
* ==============================================
* iOS9 'click', 'mousedown' and 'mouseup' fix
* ---------------------------------------------
* Include this script in your poject to fix 'click', 'mousedown' and 'mouseup' event
* handling for $(window), $(document), $('body') and $('html'). By default iOS9 Safari is
* suppressing those events in some situations and without some magic they can't be rely on.
* This fix is blocking native event handlers from firing
* (in some rare cases event will reach it's destination)
* and it handles native event handlers basing on 'touchstart' and 'touchend' event.
* ---------------------------------------------
* Use at your own risk
*/
(function($) {
$(document).ready(function() {
if (typeof navigator.userAgent == 'undefined' || !navigator.userAgent.match(/(iPad|iPhone|iPod)/i)) {
return;
}
var EVENT_NAMESPACE = 'IOS9FIX';
var MAX_DOM_DEPTH = 100;
/**
* Suppress event for $object.
* #param $object
* #param eventType
*/
var blockEventFor = function($object, eventType) {
var eventQueue, eventRepo = new Array();
if ($._data($object.get(0), "events") !== undefined) {
eventQueue = $._data($object.get(0), "events")[eventType];
}
if (eventQueue !== undefined) {
for (var i = 0; i < eventQueue.length; i++) {
eventRepo.push({
handler: eventQueue[i].handler,
selector: eventQueue[i].selector,
namespace: eventQueue[i].namespace
});
}
$object.off(eventType);
}
$object.on(eventType + '.' + EVENT_NAMESPACE, '*', function(event) {
event.stopImmediatePropagation();
});
for (var i = 0; i < eventRepo.length; i++) {
var _eventType = eventRepo[i].namespace ?
eventType + '.' + eventRepo[i].namespace :
eventType;
$object.on(_eventType, eventRepo[i].selector, eventRepo[i].handler);
}
};
var executeMockedEventHandlers = function($object, mockedEventType, originalEvent) {
/** Let's say touch is mouse left button (by default touch event has .which === 0) */
originalEvent.which = 1;
var mockedEventQueue, $target = $(originalEvent.target);
if ($._data($object.get(0), "events") !== undefined) {
mockedEventQueue = $._data($object.get(0), "events")[mockedEventType];
}
/** No event-handlers for event of such type */
if (mockedEventQueue === undefined) {
return false;
}
for (var preventEndlessLoop = 0; preventEndlessLoop < MAX_DOM_DEPTH; preventEndlessLoop++) {
/** END THE LOOP */
if ($target.length == 0) {
break;
}
/** EXECUTE MOCKED EVENT HANDLERS */
for (var i = 0; i < mockedEventQueue.length; i++) {
// Skip eventHandler used to block originalEvent for mockedEvent
if (mockedEventQueue[i].namespace === EVENT_NAMESPACE) {
continue;
}
if (mockedEventQueue[i].selector === undefined) {
// Skip $object level eventHandlers until current DOM level is $object level
if (!$target.is($object[0])) {
continue;
}
} else {
// Skip eventHandlers not meant for current DOM level
if (!$target.is(mockedEventQueue[i].selector)) {
continue;
}
}
// Execute handler for current DOM level
if (mockedEventQueue[i].handler.call($target[0], originalEvent) === false) {
originalEvent.stopImmediatePropagation();
}
// Check for stopImmediatePropagation() */
if (originalEvent.isImmediatePropagationStopped()) {
break;
}
}
if (originalEvent.isPropagationStopped()) {
break;
}
/** Go to parent level */
$target = $target.parent();
}
};
/*****************************
* INITIALIZATION
****************************/
/**
* Go through objects and suppress all selected events.
*/
$.each([$(document), $(window), $('body'), $('html')], function(objectIndex, $object) {
$.each(['mousedown', 'click', 'mouseup'], function(eventIndex, eventType) {
blockEventFor($object, eventType);
});
});
/**
* Init MouseDown-Mock for Dom $object
* #param $object
*/
var initMouseDownMock = function($object) {
$object.on('touchstart', function(event) {
executeMockedEventHandlers($object, 'mousedown', event);
});
};
$.each([$(document), $(window), $('body'), $('html')], function(objectIndex, $object) {
initMouseDownMock($object);
});
var initMouseUpMock = function($object) {
$object.on('touchend', function(event) {
executeMockedEventHandlers($object, 'mouseup', event);
});
};
/**
* Init MouseUp-Mock for objects...
*/
$.each([$(document), $(window), $('body'), $('html')], function(objectIndex, $object) {
initMouseUpMock($object);
});
/**
* MOCK CLICK EVENT
*/
/**
* Init Click-Mock for Dom $object
* #param $object
*/
var initClickMock = function($object) {
var clickCancelationTimer, isClick, cursorX, cursorY, target;
$object.on('touchstart', function(event) {
isClick = true;
cursorX = event.originalEvent.touches[0].pageX;
cursorY = event.originalEvent.touches[0].pageY;
target = event.target;
/** Click Timeout */
clickCancelationTimer = setTimeout(function() {
isClick = false;
}, 300);
});
/** moved more than 10 px away from starting position */
$object.on('touchmove', function(event) {
if (Math.abs(cursorX - event.originalEvent.touches[0].pageX) > 10 || Math.abs(cursorY - event.originalEvent.touches[0].pageY) > 10) {
isClick = false;
}
});
$object.on('touchend', function(event) {
clearTimeout(clickCancelationTimer);
if (isClick) {
executeMockedEventHandlers($object, 'click', event);
}
});
};
/**
* Init Click-Mock for objects...
*/
$.each([$(document), $(window), $('body'), $('html')], function(objectIndex, $object) {
initClickMock($object);
});
});
})(jQuery);
you can disable the tooltips for all the elements and enable it on the one you need it to be in. try this:
$('*').tooltip();
this will put a tooltip on all elements.
you can disable the tooltip from all elements like so as well:
$('*').tooltip('disable');
if you want a specific element then select it and enable/disable it. here's a question on this site that might help you as well:
Turn off jQuery UI tooltip for certain elements

jQuery: change class after conditional is met

I created this site where you have multiple sliders moving vertically using this example on stackoverflow > here < along with this fiddle.
The site when loaded has an overflow: hidden on the body and position fixed on my main content div(div class="content-fs row"). The idea is that when you first arrive on the page, you scroll through each slide and once you hit the last one, the position changes on the main content div(div class="content-fs row") from fixed to static and the overflow: hidden is removed from the body. I'm having trouble writing the conditional statement that says "if its the last slider, change the position." The jquery below is the code i'm using for the site along with the conditional statement that doesn't work.
Any pointers/advice would be greatly appreciated!
jquery:
function scrollLax(){
/*
initialize
*/
var scrollDown = false;
var scrollUp = false;
var scroll = 0;
var $view = $('#portfolio');
var t = 0;
var h = $view.height() - 250;
$view.find('.portfolio-sliders').each(function() {
var $moving = $(this);
// position the next moving correctly
if($moving.hasClass('from-bottom')) {
$moving.css('top', h); // subtract t so that a portion of the other slider is showing
}
// make sure moving is visible
$moving.css('z-index', 10);
});
var $moving = $view.find('.portfolio-sliders:first-child');
$moving.css('z-index', 10);
/*
event handlers
*/
var mousew = function(e) {
var d = 0;
if(!e) e = event;
if (e.wheelDelta) {
d = -e.wheelDelta/3;
} else if (e.detail) {
d = e.detail/120;
}
parallaxScroll(d);
}
if (window.addEventListener) {
window.addEventListener('DOMMouseScroll', mousew, false);
}
window.onmousewheel = document.onmousewheel = mousew;
/*
parallax loop display loop
*/
window.setInterval(function() {
if(scrollDown)
parallaxScroll(4);
else if(scrollUp)
parallaxScroll(-4);
}, 50);
function parallaxScroll(scroll) {
// current moving object
var ml = $moving.position().left;
var mt = $moving.position().top;
var mw = $moving.width();
var mh = $moving.height();
// calc velocity
var fromBottom = false;
var vLeft = 0;
var vTop = 0;
if($moving.hasClass('from-bottom')) {
vTop = -scroll;
fromBottom = true;
}
// calc new position
var newLeft = ml + vLeft;
var newTop = mt + vTop;
// check bounds
var finished = false;
if(fromBottom && (newTop < t || newTop > h)) {
finished = true;
newTop = (scroll > 0 ? t : t + h);
}
// set new position
$moving.css('left', newLeft);
$moving.css('top', newTop);
// if finished change moving object
if(finished) {
// get the next moving
if(scroll > 0) {
$moving = $moving.next('.portfolio-sliders');
if($moving.length == 0)
$moving = $view.find('.portfolio-sliders:last');
//this is where I am trying to add the if conditional statement.
if ('.portfolio-sliders:last')
$('.content-fs.row').css({'position': 'static'});
if('.portfolio-sliders:last' && (mt == 0))
$('html, body').removeClass('overflow');
} else {
$moving = $moving.prev('.portfolio-sliders');
if($moving.length == 0)
$moving = $view.find('.portfolio-sliders:first-child');
//reverse the logic and if last slide change position
if('.portfolio-sliders:first-child')
$('.content-fs.row').css({'position': 'fixed'});
}
}
// for debug
//$('#direction').text(scroll + "/" + t + " " + ml + "/" + mt + " " + finished + " " + $moving.text());
}
}
Your code as it is simply asks whether .portfolio-sliders:last exists. Seems you should be doing:
if ($moving == $('.portfolio-sliders:last') )
or something along those lines, instead checking whether the active slide is the last.

How do I add a class of "active" to a visible slide within a slideshow?

I have a page that is mainly a large slider, I am using unslider (unslider.com) right now, but would be willing to switch to a different slider if it provides the functionality I need. The goal is to have the slide show move through my different projects. At the bottom of the page, will be an arrow button that when clicked will slide in the specific project details for the current or visible slide. I was planning to load the project details into a hidden div via ajax based on the data attribute of the "active" slide.
The problem I am having is that I don't know how to add a class of "active" to the visible slide. I am fairly new, but I believe I will need to use javascript or jquery to change the "active" class appropriately. Here is the HTML and jQuery for the slider:
<div class="banner">
<ul>
<li class="slide_1" data-link="ajaxed_content_url">
<img src="slide_1.jpg" />
</li>
<li class="slide_2" data-link="ajaxed_content_url">
<img src="slide_2.jpg" />
</li>
<li class="slide_3" data-link="ajaxed_content_url">
<img src="slide_3.jpg" />
</li>
</ul>
<a class="details_btn" href="#"></a>
</div>
<script>
$('.banner').unslider({
speed: 500,
delay: 5000,
complete: function() {},
keys: true,
dots: true,
fluid: true
});
</script>
When the slider is rendered in the browser, an "active" class is not added to the code. Any help would be greatly appreciated.
Unslider simply animates the ul, so it does not actually change the picture li's. However, it DOES add an active class to the dots. Digging through the source code, I found where it adds the active class to the dots and edited in a similar line that should apply an active class to the pictures. Here is the edited source code:
/**
* Unslider by #idiot
*/
(function($, f) {
// If there's no jQuery, Unslider can't work, so kill the operation.
if(!$) return f;
var Unslider = function() {
// Set up our elements
this.el = f;
this.items = f;
// Dimensions
this.sizes = [];
this.max = [0,0];
// Current inded
this.current = 0;
// Start/stop timer
this.interval = f;
// Set some options
this.opts = {
speed: 500,
delay: 3000, // f for no autoplay
complete: f, // when a slide's finished
keys: !f, // keyboard shortcuts - disable if it breaks things
dots: f, // display ••••o• pagination
fluid: f // is it a percentage width?,
};
// Create a deep clone for methods where context changes
var _ = this;
this.init = function(el, opts) {
this.el = el;
this.ul = el.children('ul');
this.max = [el.outerWidth(), el.outerHeight()];
this.items = this.ul.children('li').each(this.calculate);
// Check whether we're passing any options in to Unslider
this.opts = $.extend(this.opts, opts);
// Set up the Unslider
this.setup();
return this;
};
// Get the width for an element
// Pass a jQuery element as the context with .call(), and the index as a parameter: Unslider.calculate.call($('li:first'), 0)
this.calculate = function(index) {
var me = $(this),
width = me.outerWidth(), height = me.outerHeight();
// Add it to the sizes list
_.sizes[index] = [width, height];
// Set the max values
if(width > _.max[0]) _.max[0] = width;
if(height > _.max[1]) _.max[1] = height;
};
// Work out what methods need calling
this.setup = function() {
// Set the main element
this.el.css({
overflow: 'hidden',
width: _.max[0],
height: this.items.first().outerHeight()
});
// Set the relative widths
this.ul.css({width: (this.items.length * 100) + '%', position: 'relative'});
this.items.css('width', (100 / this.items.length) + '%');
if(this.opts.delay !== f) {
this.start();
this.el.hover(this.stop, this.start);
}
// Custom keyboard support
this.opts.keys && $(document).keydown(this.keys);
// Dot pagination
this.opts.dots && this.dots();
// Little patch for fluid-width sliders. Screw those guys.
if(this.opts.fluid) {
var resize = function() {
_.el.css('width', Math.min(Math.round((_.el.outerWidth() / _.el.parent().outerWidth()) * 100), 100) + '%');
};
resize();
$(window).resize(resize);
}
if(this.opts.arrows) {
this.el.parent().append('<p class="arrows"><span class="prev">â†</span><span class="next">→</span></p>')
.find('.arrows span').click(function() {
$.isFunction(_[this.className]) && _[this.className]();
});
};
// Swipe support
if($.event.swipe) {
this.el.on('swipeleft', _.prev).on('swiperight', _.next);
}
};
// Move Unslider to a slide index
this.move = function(index, cb) {
// If it's out of bounds, go to the first slide
if(!this.items.eq(index).length) index = 0;
if(index < 0) index = (this.items.length - 1);
var target = this.items.eq(index);
var obj = {height: target.outerHeight()};
var speed = cb ? 5 : this.opts.speed;
if(!this.ul.is(':animated')) {
// Handle those pesky dots
_.el.find('.dot:eq(' + index + ')').addClass('active').siblings().removeClass('active');
//HERE IS WHAT I ADDED
_.el.find('ul li:eq(' + index + ')').addClass('active').siblings().removeClass('active');
this.el.animate(obj, speed) && this.ul.animate($.extend({left: '-' + index + '00%'}, obj), speed, function(data) {
_.current = index;
$.isFunction(_.opts.complete) && !cb && _.opts.complete(_.el);
});
}
};
// Autoplay functionality
this.start = function() {
_.interval = setInterval(function() {
_.move(_.current + 1);
}, _.opts.delay);
};
// Stop autoplay
this.stop = function() {
_.interval = clearInterval(_.interval);
return _;
};
// Keypresses
this.keys = function(e) {
var key = e.which;
var map = {
// Prev/next
37: _.prev,
39: _.next,
// Esc
27: _.stop
};
if($.isFunction(map[key])) {
map[key]();
}
};
// Arrow navigation
this.next = function() { return _.stop().move(_.current + 1) };
this.prev = function() { return _.stop().move(_.current - 1) };
this.dots = function() {
// Create the HTML
var html = '<ol class="dots">';
$.each(this.items, function(index) { html += '<li class="dot' + (index < 1 ? ' active' : '') + '">' + (index + 1) + '</li>'; });
html += '</ol>';
// Add it to the Unslider
this.el.addClass('has-dots').append(html).find('.dot').click(function() {
_.move($(this).index());
});
};
};
// Create a jQuery plugin
$.fn.unslider = function(o) {
var len = this.length;
// Enable multiple-slider support
return this.each(function(index) {
// Cache a copy of $(this), so it
var me = $(this);
var instance = (new Unslider).init(me, o);
// Invoke an Unslider instance
me.data('unslider' + (len > 1 ? '-' + (index + 1) : ''), instance);
});
};
})(window.jQuery, false);
I don't think you will be able to add an active class. However, The complete function is executed after every slide animation, try something like this:
<script>
var NB_OF_SLIDES = ...;
var i = 0;
loadAjaxForSlide i;
$('.banner').unslider({
speed: 500,
delay: 5000,
complete: function() {
i++;
if(i >= NB_OF_SLIDES){
i = 0;
}
loadAjaxForSlide i;
},
keys: true,
dots: true,
fluid: true
});
</script>
But I wouldn't consider loading data via Ajax after every slide animation, it's kinda messy. Try loading everything at once at page load.

Jquery = setInterval code works in Firefox but not in Chrome

The code (from an old plugin that I am trying to make responsive) slides a set of images across every n seconds. It uses setInterval code as below, and works well on Firefox. On Chrome it runs once only, and debugging indicates that the second setInteral function is just not called. Please help as its diving me mad. Running example at http://lelal.com/test/site10/index.html (sorry about the load time)
play = setInterval(function() {
if (!busy) {
busy = true;
updateCurrent(settings.direction);
slide();
}
}, settings.speed);
The complete plugin code is below (sorry its long)
/*
* jQuery Queue Slider v1.0
* http://danielkorte.com
*
* Free to use and abuse under the MIT license.
* http://www.opensource.org/licenses/mit-license.php
*/
(function($){
var QueueSlider = function(element, options) {
var play = false,
busy = false,
current = 2,
previous = 2,
widths = [],
slider = $(element),
queue = $('ul.queue', slider),
numImages = $('img', queue).size(),
viewportWidth = slider.width(),
settings = $.extend({}, $.fn.queueSlider.defaults, options);
$(window).resize(function(){
if(busy !== false)
clearTimeout(busy);
busy = setTimeout(resizewindow, 200); //200 is time in miliseconds
});
function resizewindow() {
viewportWidth = slider.width();
if (settings.scale > 0) {
slider.css('height',viewportWidth * settings.scale);
computeQueueWidth();
}
queue.css('left', -getQueuePosition());
busy = false;
}
function requeue() {
$('li', queue).each(function(key, value) {
$(this).attr('class', 'slide-' + (key+1));
});
}
function updateCurrent(dir) {
current += dir;
if (current < 1) {
current = numImages;
} else if (current > numImages) {
current = 1;
}
}
function getQueuePosition() {
var i = 0, index = current-1,
queuePosition = (viewportWidth - widths[index]) / -2;
for (i = 0; i < index; i++) { queuePosition += widths[i]; }
return queuePosition;
}
function computeQueueWidth() {
var queueWidth = 0;
// factor = slider.height() / settings.imageheight;
// settings.imageheight = settings.imageheight * factor;
// Get the image widths and set the queue width to their combined value.
$('li', queue).each(function(key, value) {
var slideimg = $("img", this),
slide = $(this),
// width = slide.width() * factor,
width = slideimg.width();
slide.css('width', width+'px');
queueWidth += widths[key] = width;
});
queue.css('width', queueWidth + 500);
}
function slide() {
var animationSettings = {
duration: settings.transitionSpeed,
queue: false
};
// Emulate an infinte loop:
// Bring the first image to the end.
if (current === numImages) {
var firstImage = $('li.slide-1', queue);
widths.push(widths.shift());
queue.css('left', queue.position().left + firstImage.width()).append(firstImage);
requeue();
current--; previous--;
}
// Bring the last image to the beginning.
else if (current === 1) {
var lastImage = $('li:last-child', queue);
widths.unshift(widths.pop());
queue.css('left', queue.position().left + -lastImage.width()).prepend(lastImage);
requeue();
current = 2; previous = 3;
}
// Fade in the current and out the previous images.
if (settings.fade !== -1) {
$('li.slide-'+current, queue).animate({opacity: 1}, animationSettings);
$('li.slide-'+previous, queue).animate({opacity: settings.fade}, animationSettings);
}
// Animate the queue.
animationSettings.complete = function() { busy = false; };
queue.animate({ left: -getQueuePosition() }, animationSettings);
previous = current;
}
//
// Setup the QueueSlider!
//
if (numImages > 2) {
// Move the last slide to the beginning of the queue so there is an image
// on both sides of the current image.
if (settings.scale > 0) {
slider.css('height',viewportWidth * settings.scale);
}
computeQueueWidth();
widths.unshift(widths.pop());
queue.css('left', -getQueuePosition()).prepend($('li:last-child', queue));
requeue();
// Fade out the images we aren't viewing.
if (settings.fade !== -1) { $('li', queue).not('.slide-2').css('opacity', settings.fade); }
// Include the buttons if enabled and assign a click event to them.
if (settings.buttons) {
slider.append('<button class="previous" rel="-1">' + settings.previous + '</button><button class="next" rel="1">' + settings.next + '</button>');
$('button', slider).click(function() {
if (!busy) {
busy = true;
updateCurrent(parseInt($(this).attr('rel'), 10));
clearInterval(play);
slide();
}
return false;
});
}
// Start the slideshow if it is enabled.
if (settings.speed !== 0) {
play = setInterval(function() {
if (!busy) {
busy = true;
updateCurrent(settings.direction);
slide();
}
}, settings.speed);
}
}
else {
// There isn't enough images for the QueueSlider!
// Let's disable the required CSS and show all one or two images ;)
slider.removeClass('queueslider');
}
};
$.fn.queueSlider = function(options) {
return this.each(function(key, value) {
var element = $(this);
// Return early if this element already has a plugin instance.
if (element.data('queueslider')) { return element.data('queueslider'); }
// Pass options to plugin constructor.
var queueslider = new QueueSlider(this, options);
// Store plugin object in this element's data.
element.data('queueslider', queueslider);
});
};
$.fn.queueSlider.defaults = {
scale: 0,
imageheight: 500,
fade: 0.3, // Opacity of images not being viewed, use -1 to disable
transitionSpeed: 700, // in milliseconds, speed for fade and slide motion
speed: 7000, // in milliseconds, use 0 to disable slideshow
direction: 1, // 1 for images to slide to the left, -1 to silde to the right during slideshow
buttons: true, // Display Previous/Next buttons
previous: 'Previous', // Previous button text
next: 'Next' // Next button text
};
}(jQuery));
Have a look here:
http://www.w3schools.com/jsref/met_win_setinterval.asp
The setInterval() method will continue calling the function until clearInterval() is called, or the window is closed.
Looks like you're calling clearInterval after the first usage of play, which makes it stop working.

Jquery - making tabs animate synchronously

Here is the jsfiddle demo.
I am trying to animate the tabs in my carousel synchronously, i.e. they all should slide left/right together. However, as you will notice from the demo, sometimes they do, othertimes they don't.
Could someone please point out where I am going wrong? Im not just looking for the correct code but logic & explanation please.
Ive tried to comments the code as much as I can so that its easier to follow & pinpoint the problem. The line that has the 'animate' code has the comment: // ***** NOTE -- THIS IS THE LINE THATS ANIMATING THE TABS TO SCROLL RIGHT *****
Code:
var eLeftScrollButton = document.getElementById("t_l_nav");
var eRightScrollButton = document.getElementById("t_r_nav");
var eArrowForTabs = document.getElementById("arrow");
var iActiveNo = 0; //var. for storing the active tab. no.
var iTabSlideNo = 0;
var iTabWidth = 147; // a tab's width
var eTabsDiv = document.getElementById("tabs");
var iTabsCount = eTabsDiv.childNodes.length; //tabs count
var bClickable = true; // bool whether left & right buttons are clickable or not
var iButtonsPage = 1; // button page no.
var iStonesPage = 1; // stones page no.
var iRibbonsPage = 1; // ribbons page no.
var iLacesPage = 1; // laces page no.
var iPipingPage = 1; // laces page no.
displayTabNo_onstart();
/* ---------- displaying the current tab, hiding the other non-current tabs ---------- */
function displayTabNo_onstart()
{
for ( var i = 0; i < iTabsCount; i++)
{
if (i === iActiveNo)
{
eTabsDiv.children[i].style.color = "black";
eTabsDiv.children[i].style.fontWeight = "bold";
} else
{
eTabsDiv.children[i].style.opacity = "0.2";
eTabsDiv.children[i].style.fontWeight = "normal";
}
}
}
/* ---------- activate the button, ribbons etc based on what tab is active right now, & hide others ---------- */
function activateFeaturesContainer (direction)
{
var eFeaturesContainerDiv = document.getElementById("features");
eFeaturesContainerDiv.children[iActiveNo].style.display = "block";
(direction === "right") ? ((eFeaturesContainerDiv.children[iActiveNo - 1].style.display = "none") & (bClickable = true)) : ((eFeaturesContainerDiv.children[iActiveNo + 1].style.display = "none") & (bClickable = true));
}
/* ---------- called when the right button for tabs is pressed, calls the below two 'right' functions ---------- */
function pressRightButton ()
{
if (bClickable === true)
{
bClickable = false;
pressRightButtonEffect();
activateRightTab();
} else {
return;
}
}
/* ---------- called when the left button for tabs is pressed, calls the below two 'left' functions ---------- */
function pressLeftButton ()
{
if (bClickable === true)
{
bClickable = false;
pressLeftButtonEffect();
activateLeftTab();
} else {
return;
}
}
/* ---------- effect on right button when pressed ---------- */
function pressRightButtonEffect()
{
eRightScrollButton.style.top = "29px";
window.setTimeout(function()
{
var eStyle = window.getComputedStyle(eRightScrollButton);
var pBackgroundColorProperty = eStyle.backgroundColor; // getting the CSS backgroundColor
eRightScrollButton.style.top = "28px";
}, 150);
}
/* ---------- effect on left button when pressed ---------- */
function pressLeftButtonEffect()
{
eLeftScrollButton.style.top = "29px";
window.setTimeout(function()
{
var eStyle = window.getComputedStyle(eLeftScrollButton);
var pBackgroundColorProperty = eStyle.backgroundColor; // getting the CSS backgroundColor
eLeftScrollButton.style.top = "28px";
}, 150);
}
/* ---------- tabs indicator, tabs & other animations on right button when pressed ---------- */
function activateRightTab()
{
var direction = "right";
if (iActiveNo < iTabsCount - 1 && iActiveNo >= 0)
{
iActiveNo = iActiveNo + 1;
(iActiveNo > 0) ? eLeftScrollButton.childNodes[0].setAttribute("src", "Img/WA03_Container_LeftScrollButton_Active.png") : false; //reinstate leftScrollbutton to active
(iTabSlideNo < iTabsCount - 1) ? iTabSlideNo++ : iTabSlideNo;
// ***** NOTE -- THIS IS THE LINE THATS ANIMATING THE TABS TO SCROLL RIGHT *****
$(".c_tabs").animate ({"right": ("+=147px")}, 500, "swing", function()
{
$(eTabsDiv.childNodes[iActiveNo]).animate ({"opacity" : "1"}, 191,"linear");
$(eTabsDiv.childNodes[iActiveNo - 1]).animate ({"opacity" : "0.2"}, 191,"linear");
});
window.setTimeout (function ()
{
eTabsDiv.childNodes[iActiveNo].style.fontWeight = "bold";
eTabsDiv.childNodes[iActiveNo-1].style.fontWeight = "normal";
},500);
$(eArrowForTabs).animate ({"top" : "69px"}, 191, "linear", function()
{
window.setTimeout (function()
{ $(eArrowForTabs).animate ({"top" : "55px"}, 191, "linear"); }, 75);
});
(iTabSlideNo + 1 === iTabsCount) ? eRightScrollButton.childNodes[0].setAttribute ("src", "Img/WA02_Container_RightScrollButton_Passive.png"):false;
window.setTimeout (function() {activateFeaturesContainer(direction);}, 600);
} else {
bClickable = true;
} // close -> first if statement of this function
if (iActiveNo === iTabsCount - 1 && eRightScrollButton.childNodes[0].getAttribute("src") === "Img/WA02_Container_RightScrollButton_Passive.png") //springy effect on last tab
{
$(eTabsDiv.childNodes[iActiveNo]).animate({"right" : (((iTabSlideNo * iTabWidth) + 10) + "px")}, 100).animate({"right" : (((iTabSlideNo * iTabWidth) - 5) + "px")}, 45).animate({"right" : (((iTabSlideNo * iTabWidth) + 0) + "px")}, 10);
} // close -> springy effect if statement
} // close -> activateRightTab function
/* ---------- tabs indicator, tabs & other animations on left button when pressed ---------- */
function activateLeftTab()
{
var direction = "left";
if (iActiveNo <= iTabsCount -1 && iActiveNo > 0) //because length doesn't count 0 & we are substracting 1 below
{
iActiveNo = iActiveNo - 1;
(iActiveNo < iTabsCount - 1) ? eRightScrollButton.childNodes[0].setAttribute("src", "Img/WA01_Container_RightScrollButton_Active.png") : false; (iTabSlideNo > 0) ? iTabSlideNo-- : false;
$(".c_tabs").animate ({"right": ("-=147px")}, 500, "linear", function()
{
$(eTabsDiv.childNodes[iActiveNo]).animate ({"opacity" : "1"}, 250,"linear");
$(eTabsDiv.childNodes[iActiveNo + 1]).animate ({"opacity" : "0.2"}, 250,"linear");
});
window.setTimeout ( function ()
{
eTabsDiv.childNodes[iActiveNo].style.fontWeight = "bold";
eTabsDiv.childNodes[iActiveNo-1].style.fontWeight = "normal";
},500);
$(eArrowForTabs).animate ({"top" : "69px"}, 191, "linear", function()
{
window.setTimeout( function()
{ $(eArrowForTabs).animate ({"top" : "55px"}, 191, "linear"); }, 75);
});
(iTabSlideNo === 0) ? eLeftScrollButton.childNodes[0].setAttribute ("src", "Img/WA04_Container_LeftScrollButton_Passive.png") : false;
window.setTimeout( function() {activateFeaturesContainer(direction)}, 600);
} else { // close -> first if statement of this function
bClickable = true;
}
if (iActiveNo === 0 && eLeftScrollButton.childNodes[0].getAttribute("src") === "Img/WA04_Container_LeftScrollButton_Passive.png") //springy effect on last tab
{
$(eTabsDiv.childNodes[iActiveNo]).animate({"right" : (((iTabSlideNo * iTabWidth) - 10) + "px")}, 100).animate({"right" : (((iTabSlideNo * iTabWidth) + 5) + "px")}, 45).animate({"right" : (((iTabSlideNo * iTabWidth) + 0) + "px")}, 10);
} // close -> springy effect if statement
} // close -> activateRightTab function

Categories

Resources