There are two elements on this page that have Javascript attached. The donate box on the left, and the image slider in the centre. The image slider just rolls round on a time delay while the donate box changes its left-position on hover, then returns when hover is released. This works OK in FF and Chrome.
In IE there seems to be some sort of clash between the two elements. As soon as I run the hover command the slider stops working. The hover also only works once, and needs a page refresh before it'll run again.
Is there any way to fix this?
This is the code for the image slider:
<script type="text/javascript">
$(document).ready(function() {
//Set Default State of each portfolio piece
$(".paging").show();
$(".paging a:first").addClass("active");
//Get size of images, how many there are, then determin the size of the image reel.
var imageWidth = $(".window").width();
var imageSum = $(".image_reel img").size();
var imageReelWidth = imageWidth * imageSum;
//Adjust the image reel to its new size
$(".image_reel").css({'width' : imageReelWidth});
//Paging + Slider Function
rotate = function(){
var triggerID = $active.attr("rel") - 1; //Get number of times to slide
var image_reelPosition = triggerID * imageWidth; //Determines the distance the image reel needs to slide
$(".paging a").removeClass('active'); //Remove all active class
$active.addClass('active'); //Add active class (the $active is declared in the rotateSwitch function)
//Slider Animation
$(".image_reel").animate({
left: -image_reelPosition}, {
duration: 2000,
easing: 'easeInOutQuad'
})
}
//Rotation + Timing Event
rotateSwitch = function(){
play = setInterval(function(){ //Set timer - this will repeat itself every 3 seconds
$active = $('.paging a.active').next();
if ( $active.length === 0) { //If paging reaches the end...
$active = $('.paging a:first'); //go back to first
}
rotate(); //Trigger the paging and slider function
}, 6000); //Timer speed in milliseconds (3 seconds)
};
rotateSwitch(); //Run function on launch
//On Hover
$(".image_reel a").hover(function() {
clearInterval(play); //Stop the rotation
}, function() {
rotateSwitch(); //Resume rotation
});
//On Click
$(".paging a").click(function() {
$active = $(this); //Activate the clicked paging
//Reset Timer
clearInterval(play); //Stop the rotation
rotate(); //Trigger rotation immediately
rotateSwitch(); // Resume rotation
return false; //Prevent browser jump to link anchor
});
});
</script>
and this is for the donate box:
$(document).ready(function() {
$('#donatebox').hover(function() {
$('#donatebox').animate({
'left': parseInt($(this).css('left'),10) == 295 ?
$(this).animate({'left': '0px'}, 1000,'easeOutQuad') :
295
});
});
});
It's beyond me so I've worked round it another way that doesn't need parsing (which I really don't understand...)
$(document).ready(function() {
$('#donatebox').mouseenter(
function() {
$('#donatebox').animate({"marginLeft": -5}, 1000, "easeOutBounce");
});
});
$(document).ready(function() {
$("#donatebox").mouseleave (
function() {
$(this).animate({"marginLeft": -5}, 20).animate({"marginLeft": -305}, 700, "easeOutQuad");
});
});
Something's causing a Javascript error in your jQuery "easing" plugin, when the div has eased back into its slot. This is why no scripts are running after you use the Donate box once.
If you use Developer Tools in IE, you'll find that the error is caught. Then (although the animation is decoupled so you can't just go up the callstack) it is deducible that the issue is in the animation that you instigate from your custom.js:
$('#donatebox').animate({
'left': parseInt($(this).css('left'),10) == 295 ?
$(this).animate({'left': '0px'}, 1000,'easeOutQuad') :
295
});
^ Doesn't look right to me.
You also have duplicate HTML node IDs overimage. IDs are unique; perhaps you meant to use classes?
Maybe it help you.
Ticket on jQuery Bug Tracker
This is caused by Invalid Argument exception on Line: 8538 of jquery-latest.js
Related
I have an image embedded in a container with a background image to give the effect of scrolling within the page. Initially, I had the scrolling effect take place on page load, with this simple bit of script which worked perfectly.
$(window).on("load", function () {
$(".embedded_scroller_image").animate({ scrollTop: $('.embedded_scroller_image')[0].scrollHeight}, 2500, "easeInOutCubic");
}); // end on load
However, the element is too far down the page now and I want that animation to fire when the element enters 80% of the viewport. That part is also working fine with this code here (I'm using a scroll limiter to improve browser performance)
// limit scroll call for performance
var scrollHandling = {
allow: true,
reallow: function() {
scrollHandling.allow = true;
},
delay: 500 //(milliseconds) adjust to the highest acceptable value
};
$(window).on('scroll', function() {
var flag = true;
if(scrollHandling.allow) { // call scroll limit
var inViewport = $(window).height()*0.8; // get 80% of viewport
$('.embedded_scroller_image').each(function() { // check each embedded scroller
var distance = $(this).offset().top - inViewport; // check when it reaches offset
if ($(window).scrollTop() >= distance && flag === true ) {
$(this).animate({ scrollTop: $(this)[0].scrollHeight}, 2500, "easeInOutCubic"); //animate embedded scroller
flag = false;
}
});
} // end scroll limit
}); // end window scroll function
The problem is this: I want the autoscroll to happen once and then stop. Right now, it works on entering viewport, but if I then try to manually scroll the image, it keeps pushing back down or stutters. You can't get the element to scroll normally. I attempted to use the flag in the code to stop the animation, but couldn't get that to successfully work.
How can I have this animation fire when the element is 80% in the viewport, but then completely stop after one time?
Here is a codepen I mocked up as well http://codepen.io/jphogan/pen/PPQwZL?editors=001 If you scroll down, you will see the image element autoscroll when it enters the viewport, but if you try to then scroll that image up in its container, it won't work.
Thanks!
I have tweaked your script a bit:
// limit scroll call for performance
var scrollHandling = {
allow: true,
reallow: function() { scrollHandling.allow = true; },
delay: 500 //(milliseconds) adjust to the highest acceptable value
};
$(window).on('scroll', function() {
if(scrollHandling.allow) { // call scroll limit
var inViewport = $(window).height()*0.8; // get 80% of viewport
$('.embedded_scroller_image').each(function() { // check each embedded scroller
var distance = $(this).offset().top - inViewport; // check when it reaches offset
if ($(window).scrollTop() >= distance ) {
$(this).animate({ scrollTop: $(this)[0].scrollHeight}, 2500, "easeInOutCubic"); //animate embedded scroller
scrollHandling.allow = false;
}
});
} // end scroll limit
}); // end window scroll function
I have kicked out your flag and simply made use of scrollHandling.allow declared already.
Try if it works for you :)
Cheers!
I have custom buttons that replaces the browser scrollbar. The idea is so that scrolling oversize elements in a page wouldn't result to a dozen scroll bar on a page.
See: https://jsfiddle.net/bwgxs6ng/
Since I must show some code sample (according to some SO error message), see this:
$('.right').on('click', function(event) {
var target = $(".image-container");
var current_x = target.scrollLeft();
if( target.length ) {
event.preventDefault();
$(target).animate({
scrollLeft: current_x+100
}, 500);
}
});
It's very simple, basically it takes current scroll position of the parent, and add x to it based on the direction that's clicked.
However, going further, I want it to imitate the hold and continuous scroll, but I'm not sure how to do it.
1) What is the mouse hold event called? (OK, this part is answered, it's called MouseDown as someone point out of the duplicate)
2) What is the continuous scrolling called, and how can I do something that'd imitate the browser's continuous scroll?
You can just call .animate() repeatedly (with easing set to linear, for smooth movement) inside your setInterval() callback. Just arrange for the interval to be equal to the animation duration, so that the next animation starts just when the previous one ends.
Or, better yet, make the interval shorter (say, 50 ms or less) and just call .prop() instead of .animate(), effectively performing your own animation. (This is how jQuery implements animation internally, anyway.)
Anyway, here's how I'd rewrite your code to support smooth continuous scrolling:
var speed_x = 0, speed_y = 0;
var timer = null;
var target = $(".image-container");
function scroll() {
if (speed_x == 0 && speed_y == 0) return;
var current_x = target.scrollLeft();
var current_y = target.scrollTop();
target.prop({
scrollLeft: current_x - speed_x,
scrollTop: current_y - speed_y
});
}
$('.control').on('mouseover mouseout', function (event) {
var $this = $(this);
var speed = (event.type == 'mouseover' ? 10 : 0)
if ($this.hasClass('left')) speed_x = +speed;
if ($this.hasClass('right')) speed_x = -speed;
if ($this.hasClass('up')) speed_y = +speed;
if ($this.hasClass('down')) speed_y = -speed;
}).on( 'mousedown', function () {
scroll();
if (timer !== null) clearInterval(timer);
timer = setInterval(scroll, 50);
return false;
});
$(document).on('mouseup', function () {
if (timer !== null) clearInterval(timer);
timer = null;
});
Note how the animation is started and stopped in the mousedown and mouseup handlers, but the direction of movement is set on mouseover and mouseout. This allows you to change the scrolling direction while holding the mouse down, by dragging the cursor from one edge to another.
(For bonus points, add divs with e.g. class="control up left" in the corners of the scroll area, so that holding the mouse down over those corners will allow you to scroll diagonally. The JS code above already supports it.)
you need to set an interval on mousedown, and clear the interval on mouseup, as done in this fiddle for left and right.
The relevant code change is that we removed the click event and replaced it with
$('.left').on('mousedown', function(event) {
... scroll code ...
interval = setInterval(function(){
... scroll code ...
},500);
})
.on('mouseup',function(){clearInterval(interval);});
I'm making a simple image slider for the landing page of a website. There are two effects taking place. First, the image transitions by fading the current one in and the subsequent one out, using setInterval. There are also arrow buttons that, when clicked, slide the images forward or backward. The fading is working just fine, but the sliding functions are leaving the images in the offscreen position. Here are:
function slidePrevPic(dur){
var currentPic = $('.active-pic');
var prevPic = currentPic.prev();
if(prevPic.length == 0){
prevPic = $('#pics img').last();
}
$('.arrow').css('pointer-events','none');
setTimeout(function(){
$('.arrow').css('pointer-events','auto');
},dur);
w = $(window).width();
prevPic.css('opacity',.4);
prevPic.css('left',-w);
prevPic.animate({
'left': 0
}, dur);
currentPic.animate({
'left': w
}, dur);
setTimeout(function(){
currentPic.css('left',0);
currentPic.css('opacity',0);
},dur);
prevPic.addClass('active-pic');
currentPic.removeClass('active-pic');
};
function slideNextPic(dur){
var currentPic = $('.active-pic');
var nextPic = currentPic.next();
if(nextPic.length == 0){
nextPic = $('#pics img').first();
}
$('.arrow').css('pointer-events','none');
setTimeout(function(){
$('.arrow').css('pointer-events','auto');
},dur);
w = $(window).width();
nextPic.css('opacity',.4);
nextPic.css('left',w);
nextPic.animate({
'left':0
},dur);
currentPic.animate({
'left':-w
},dur);
setTimeout(function(){
currentPic.css('left',0);
currentPic.css('opacity',0);
},dur);
nextPic.addClass('active-pic');
currentPic.removeClass('active-pic');
};
I was trying to simplify everything to figure out what was wrong, so instead of hiding and showing images or fading them in and out, I'm just animating and setting the opacity. The idea here is pretty simple. All of the pictures are in the same place and all but one have 0 opacity. When the slider is called, the next image is moved offscreen, the current and next image are animated together (moving the current image offscreen), then the position of the current image should be reset. The sliding effect is working well, but the position of the current image is not reset, so that when it cycles back the image space goes white. I am still generally confused about how the timing of function execution with jquery and js is managed, so any help in that general direction is also much appreciated. Also, here is the code that calls these functions:
var picInterval = setInterval(function(){
fadeNextPic(picFadeTime);
},idleTime);
$('#banner #right-arrow').click(function(){
clearInterval(picInterval);
slideNextPic(picSlideTime);
picInterval = setInterval(function(){
fadeNextPic(picFadeTime);
},idleTime);
});
$('#banner #left-arrow').click(function(){
clearInterval(picInterval);
slidePrevPic(picSlideTime);
picInterval = setInterval(function(){
fadeNextPic(picFadeTime);
},idleTime);
});
So I have a slideshow on my website with images with no links. It also has buttons on the bottom to navigate to the other pictures, one for each image. I am trying to add another image, this one with a link to another part of the website. I would believe to add the picture
to the list of
<img src="/images/home-slideshow/photo-01.jpg" alt="" width="684" height="325">"
<img src="/images/home-slideshow/photo-02.jpg" alt="" width="684" height="325">"
"
I would just add the same but add
<img src="/image/home-slideshow/photo-06.jpg" alt="" width ="684" height="325">
The question I had was is there anything else I have to change somewhere else?
Also, I have to add a button for that image, would adding this linked photo to the slideshow affect the buttons in some weird way?
EDIT:
here is my slideshow javascript. But it doesnt look like it makes them strictly images?
$(document).ready(function() {
//Show the paging and activate its first link
$(".paging").show();
$(".paging a:first").addClass("active");
//Get size of the image, how many images there are, then determine the size of the image reel.
var imageWidth = $(".window").width();
var imageSum = $(".image_reel img").size();
var imageReelWidth = imageWidth * imageSum;
//Adjust the image reel to its new size
$(".image_reel").css({'width' : imageReelWidth});
//Paging and Slider Function
rotate = function(){
var triggerID = $active.attr("rel") - 1; //Get number of times to slide
var image_reelPosition = triggerID * imageWidth; //Determines the distance the image reel needs to slide
$(".paging a").removeClass('active'); //Remove all active class
$active.addClass('active'); //Add active class (the $active is declared in the rotateSwitch function)
//Slider Animation
$(".image_reel").animate({
left: -image_reelPosition
}, 500 );
};
//Rotation and Timing Event
rotateSwitch = function(){
play = setInterval(function(){ //Set timer - this will repeat itself every 7 seconds
$active = $('.paging a.active').next(); //Move to the next paging
if ( $active.length === 0) { //If paging reaches the end...
$active = $('.paging a:first'); //go back to first
}
rotate(); //Trigger the paging and slider function
}, 7000); //Timer speed in milliseconds (7 seconds)
};
rotateSwitch(); //Run function on launch
//On Hover
$(".image_reel a").hover(function() {
clearInterval(play); //Stop the rotation
}, function() {
rotateSwitch(); //Resume rotation timer
});
//On Click
$(".paging a").click(function() {
$active = $(this); //Activate the clicked paging
//Reset Timer
clearInterval(play); //Stop the rotation
rotate(); //Trigger rotation immediately
rotateSwitch(); // Resume rotation timer
return false; //Prevent browser jump to link anchor
});
});
I'm am trying to make my javascript/jquery slider button deactivated when it reaches the the end of the scrolling images( when the images have moved all the way to the right, the MoveRight button must be deactivated and only leave MoveLeft button active, same for the move LeftButton), can anybody help with this ? Im not sure if im using
.attr() and removeAttr() correctly. I have pasted my code below.
<script type="text/javascript">
$(document).ready(function(){
//Check width of Gallery div
var galleryWidth = $("#Gallery").innerWidth();
//Check width of GalleryItem
var NoListed = $("ul.GalleryItem li").length;
var galleryItemWidth = 1881;
$('.MoveRight')
$('.GalleryItem').css('width', galleryItemWidth);
//Check width of Gallery div on resize
$(window).resize(function(){
var galleryWidth = $("#Gallery").innerWidth();
});
$('.MoveLeft').click(function() {
$(".GalleryItem2").animate({"left": "-=350px"}, "slow");
$(".GalleryItem3").animate({"left": "-=280px"}, "slow");
$(".GalleryItem").animate({
left: '-=230',
}, "slow", function() {
position = $(".GalleryItem").position();
galleryItemLeft = position.left;
if(galleryItemLeft <= galleryWidth - galleryItemWidth) {
$('.MoveLeft').removeAttr('disabled');}
else{
$('.MoveLeft').attr('disabled','disabled');
$('.MoveRight').attr('disabled','disabled');
}
});
});
$('.MoveRight').click(function() {
$(".GalleryItem2").animate({"left": "+=350px"}, "slow");
$(".GalleryItem3").animate({"left": "+=280px"}, "slow");
$(".GalleryItem").animate({
left: '+=230',
}, "slow", function() {
position = $(".GalleryItem").position();
galleryItemLeft = position.left;
if(galleryItemLeft >= "0") {
$('.MoveLeft').removeAttr('disabled');}
else{
$('.MoveLeft').attr('disabled','disabled');
$('.MoveRight').attr('disabled','disabled');
}
});
});
});
</script>
first of all, I see you doing the following:
//Check width of Gallery div on resize
$(window).resize(function(){
var galleryWidth = $("#Gallery").innerWidth();
});
I like the fact that you keep your variables local, but the var keyword should be omitted in this case. You've declared galleryWidth already in the function that encloses this resize callback, so by omitting the var keyword here, the value will be assigned to the variable you use in your script, with this va keyword, you create a new galleryWidth variable, only visible in the resize callback, and therefore never used.
now for the enabling and disabling of the buttons:
you could keep a currentitem counter, and update it every time the moveright or moveleft buttons are clikced. When this counter reaches 0, you disable the moveleft button, when it reaches the number of items, you disable the moveright button, and enable them otherwise.