I have built a parallax scrolling intro for a clients website - the site contains many high res images - so I have created a quick loader which blanks out the screen with a full screen high z-index div and then uses the setTimeout method to fade in the page 4 seconds after document ready (not sure if this is the best way to do this but it works in every test I've tried).
I would like to disable the scroll to prevent users scrolling through the animation before it appears -can anyone recommend a good cross-browser method to do this?
If you want to fade in when all images are loaded, you can try this
var images = $('img');
var images_nbr = images.length;
images.load(function() {
images_nbr--;
if (images_nbr == 0) {
$('body').css('overflow','auto');
$('...').fadeIn();
}
});
Set
#mydiv {
overflow:hidden
}
in your parent div in CSS. Then, in your document, add this...
$('#mydiv').css('overflow', 'auto');
...in the function that fades in your content.
Thus, on load the page will be unscrollable, but when you fade in, the overflow property will be overwritten and allow the content to scroll.
.scrolldiv{
overflow:hidden;
}
$(window).load(function(){
$(".scrolldiv").css("overflow","auto");
});
You can try like,
initially add the below css on body
body {overflow:hidden;}
and after your setInterval function complete execution (whatever your loading function) just remove the style from body, like
$('body').css('overflow','auto');
Related
I'm using jQuery mobile.
How can I make footer disappear while scroll is active?
When scrolling stops I want to show footer again.
HTML snippet looks like this:
<div id="footer" data-role="footer" data-position="fixed" data-corners="false">
Use $.scroll to hide the footer whilst scrolling and setTimeout to show it again once scrolling stops:
var scrolling;
$(window).scroll(function() {
clearTimeout(scrolling);//clear any existing timeout
$("#footer").hide();
scrolling = setTimeout(function(){$("#footer").show();},100);//set the timeout to hide the footer (will be cancelled if scrolling continues)
})
http://jsfiddle.net/c6uqdhjo/1/
Use the jquery scroll event.
You can find information in the docs: http://api.jquery.com/scroll/
Something along the lines of (not tested!):
$(window).scroll(function() {
$("#footer").hide();
});
See Test Page
var pageIsScrolling = (function(){
var timer, body = $(document.body);
return function(){
clearTimeout(timer);
timer = setTimeout(scrollEnd, 250);
body .addClass('scrolling');
}
function scrollEnd(){
timer = null;
body.removeClass('scrolling');
}
})();
$(window).on('scroll.scrolling', pageIsScrolling);
Now whenever you start scrolling, the body has the class scrolling and you can target that in your CSS, like so:
.scrolling > footer{ opacity:0; }
or even add transition for your footer so it would look smoother.
(I'm pretty sure this should also work with jQuery mobile)
notes:
I could work directly on the footer element from javascript, but I believe working with general state classes is a better way to change states across an application, and then you can derive from that whatever you want in your CSS, so, here, the desired state class was "scrolling".
I am using custom event namespace here, which is a good practice
using element caching (body)
scrollEnd function is separated and isn't directly written inside the setTimeout for better readability.
I've looked at some similar posts regarding interaction delay after page load, but I can't seem to find anything regarding the classical a:hover disable.
The problem is that JS will load most likely slower than the CSS, and hacking CSS isn't going to work for this problem.
Situation
I have a home page animation. On page load, i have a stack of images coming in from the left and a div of absolute anchor tags coming in from the right (~ 2 cases per line), which both slide and meet in the middle. After page load, I set a timer to go through the stack of images, and the corresponding anchor tag highlights.
The problem is that this timer is broken when the user hovers over any of the anchors tags, and when this happens, the corresponding image fades in. And this interaction could be right on page load.
Is there any possible way of disabling anchors tags a:hover on page load/delay?
What I've tried
I cannot simply remove the a:hover class and replace it with another one of background-color:transparent, because my JS still picks up the onHover function (I could target onHover only for that changed class maybe..)
I am able to target each of the anchor tags on page load with an alert on mouseenter when accidentally hovering over:
//on page load, disable mouse-over ability on anchor tags
var disableOnLoad = function (ev) {
var target = $(ev.target);
var casesId = target.attr('id');
//if mouse is over one of the cases
if (target.is(".cases")) {
//disable CSS a:hover
$(this).removeClass('homeText a:hover');
}
}
Another thing I might be able to try is calling setTimeOut(function(){ onHover()) so that there is a delay, but that will effect after page load as well.
Any suggestions?
CSS:
#blocker{
position:fixed;
width:100%;
height:100%;
left:0;
top:0;
right:0;
bottom:0;
z-index:9999;
}
JS:
setTimeout(function(){
$('#blocker').remove();
}, 3000);
HTML:
<body>
<div id="blocker" ></div>
<!-- your stuff -->
make sure the blocker div is close to the body tag to insure no capture/bubbling issues.
What if your page started out with your links as NOT wrapped with anchor tags, and you use a setTimeout onLoad to append the tags 3 seconds later?
Have not tested this but prevent default may work for you"
$("a").mouseover(function(event) {
event.preventDefault();
// Run any other needed code here
});
(function(){
$("a").unbind('mouseover');
}).delay(2000); // delay 2 seconds
Better to run the unbind code after you know all images are loaded
you may also want to modify the selector from all a tags to a.class
Bit late to the discussion, but in case it helps anyone else, I solved my problem by adding pointer-events: none to the body element in CSS (using a class called pointer-none, and then removing it with JavaScript after a delay.
var timeout;
window.onload = function(){
timeout = setTimeout(function(){
document.querySelector('body').classList.remove('pointer-none');
}, 1500);
}
I want a solution either using a hashtag pointing at the name of an anchor tag or javascript.
The javascript I am currently using looks like this window.scroll(0, 20000);. The problem is that this causes the window jerk down when a user arrives on the page.
I know there are jQuery animations that make this movement more gradual. However, what I want is something that makes the movement of the window imperceptible to the user. I want to be as if the user landed at the bottom of the page.
The problem you face is that you wish to go to the bottom of your page which has not loaded yet. I would consider loading the page in a hidden format then show it when it has all loaded and after scrolling the user at the location you want. Use the focus or scroll to methods.
Take a look at the filament group website.
http://filamentgroup.com/
they hide the page with a loading screen until it is ready.
This way there is no jerk.
Hope this helps.
In loop it works, if the page is fully loaded and shown:
for(var n=0;n<1000;n++) window.scrollBy(0,20);
(Notice that 20*1000=20000, which was the original place to scroll.)
Teemu's answer doesn't seem to work for me (it goes straight to the bottom, making the loop with scrollBy stepping invisible), because it doesn't implement a delay.
If you mean to animate from top to bottom of the page in a 1000ms, try something more like this:
for (var n = 0; n < 1000; n += 1) {
setTimeout(function () {
window.scrollBy(0, document.height / 1000);
}, n);
}
That will give a 1 second (1000ms) animation, scrolling to the bottom in roughly 1000 steps.
Hi I use the following code to create a slideshow with multiple DIV elements:
var $ = jQuery.noConflict();
function fadeContent() {
$(".slideshow .asset-abstract:first").fadeIn(500).delay(2000).fadeOut(500, function() {
$(this).appendTo($(this).parent());
fadeContent();
});
}
fadeContent();
The slideshow works properly but there's a problem. When the delay(2000) trigger a fadeIn-fadeOut, the page scrolls up!
What can I do to prevent this?
I think when the element fades out it does not take a real estate on the page. The element beneath it will take its place and you feel like the page scrolled. You can have a wrapper to the element you are trying to fadeIn/fadeOut and provide an appropriate height to this wrapper element. But this is not a good UX because when the element will fadeOut there will be empty section on the page.
Its because the fadeOut method ends op settings display:none; on the element.
If you force display block in css this will not happen:
Css:
.slideshow .asset-abstract:first-child {
display:block;
}
Is it possible to load a background-image asynchronously?
I've seen many jQuery plugins to load normal image in an asynchronous way, but I can't find if it's possible to preload / asynchronously load a background-image.
EDIT
I clarify my problem. I've been working on this test site http://mentalfaps.com/
The background image is loaded randomly from a set of images refreshed each hour by a chron job (which takes random images on a flickr catalog).
The host is free and slow at the moment, so the background image takes some time to load.
The positioning of the first overlay (the one with the PNG transparent mentalfaps logo) and width are regulated by a function created in the jQuery(document).ready construct.
If you try to refresh the page many times, the width of the right overlay div is 0 (and so you see a "hole" in the layout)
Here is the method to set my positions:
function setPositions(){
var oH = $('#overlay-header');
var overlayHeaderOffset = oH.offset();
var overlayRightWidth = $(window).width() - (overlayHeaderOffset.left + oH.width());
if (overlayRightWidth >= 0) {
$('#overlay-right').width(overlayRightWidth);
} else {
$('#overlay-right').width(0);
}
var lW = $('#loader-wrapper');
lW.offset({
left: (overlayHeaderOffset.left + oH.width() - lW.width())
});
}
The problem is that the $(window).width() is lower then the effective window width! so the check fails and the script goes for $('#overlay-right').width(0);
any ideas?
Not sure whether I really understand your question, but background images (and all other images) are already loaded asynchronously - the browser will start separate requests for them as soon as it encounters the URL while parsing the HTML.
See this excellent answer for background on loading order: Load and execution sequence of a web page?
If you meant something else, please clarify.
The trick to loading something in the background is to load it once, so the next time when it is loaded it already is in the cache.
Put the following at the end of your html:
<script>
var img = new Image();
img.onload = function () {
document.getElementsByTagName('body')[0].style.backgroundImage = 'background.png';
};
img.src = 'background.png';
</script>
You could use a prefetch link in the head.
<link rel="prefetch" href="/images/background.jpg">
You should be able to add these links to the head via JavaScript.
I like to use CSS to fill the background with a color for page load.
After DOM ready event, I use jQuery to modify the CSS and add a background image. That way, the image isn't loaded until after page loads. Not sure about async, but this method gives the user a decent experience.
Example: http://it.highpoint.edu/
The right side navigation links have a background image. The page initializes with a background color. It is replaced with a background image after page load, via jQuery.
changes in this file jquery.ImageOverlay.js
set your height and width and enjoy this...
imageContainer.css({
width : "299px",
height : "138px",
borderColor : hrefOpts.border_color
});
As it is already mentioned, the background image is loaded asynchronously. If you need to load the background image from JQuery code you may also set the addClass() method to set a CSS class or attr("style=\"background-image:url('myimage.png')\"")
Ive found the answer myself, it was a problem due to the .offset() method that gived sometimes the wrong values.
I had the write values using the .position() :
var overlayHeaderOffset = oH.position();