Animated background image with jQuery

by Jean. 86 Comments -

If you’re used to work with the jQuery library, there’s no doubt that you know how powerful it is. In this tutorial, we are going to create a basic web page layout which includes a super cool animated background image, using jQuery.

Getting ready

In this tutorial, we are going to create a simple layout for a website, which includes a very cool animated background. Here is how the final result will look:

As you can see, in this example I have used the Twitter background clouds, which look really nice.
This tutorial has been inspired by the one called How To Build an Animated Header in jQuery that I definitely recommend you go check out.

Let’s do it

1. The first step of this tutorial is to download our background image. I have used this one from Twitter, but of course feel free to use any other image you’d like.

2. Once finished, let’s create a a file called index.html. In order to get started with the basic HTML structure, paste the following code in your file:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
	<head>
		<meta http-equiv="Content-type" content="text/html; charset=utf-8" />
		<title>Animated background Image</title>
	</head>

	<body>
	</body>
</html>

3. Now, let’s define our document structure. Since we want to do a simple layout, we’ll only need to create a header and content area. Paste the following within the <body> and </body> tags:

<div id="container">
	<div id="header">
		<h1>Animated Background Image</h1>
	</div><!-- #header -->

	<div id="content">
		<!-- Your content will go here -->
	</div><!-- #content -->
</div><!-- #container -->

4. Well done! We already have our XHTML. Now, what we have to do is obviously use some CSS and give style to our document.
To do so, copy the code below and paste it within the <head> and <head> tags of the index.html file.

<style type="text/css" media="screen">
	body{
		background-color: #C0DEED;
		margin:0;
		padding:0;
	}

	#header{
		height:180px;
		background: #8EC1DA url(bg-clouds.png) repeat-y scroll left top;
		text-align:center;
		margin-top:-30px;
	}

	#header h1{
		padding-top:35px;
		font-family: "Myriad Pro", Helvetica, Arial, sans-serif;
		color:white;
		font-size:45px;
	}

	#content{
		background-color:#fff;
		height:500px;
		width:980px;
		margin:25px auto 0 auto;
		-moz-border-radius:10px;
		-webkit-border-radius:10px;
	}
</style>

5. At this point, you can save your work and take a look at the index.html page using your web browser. If everything is ok, your index.html page should look like the screenshot above, with fixed clouds, of course.

6. Now, it’s time to give life to the layout by using the power of jQuery. As you probably guessed it, what we have to do right now is include the library. Since Google hosts a version that you can use, there’s definitely no need to download a copy. Just use the one from Google.

To do so, paste the following line of code in your index.html file, after the closing </body> tag:

<script src="http://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js" type="text/javascript" charset="utf-8"></script>

7. Now that jQuery has been loaded, we can code a function to animate the background. Copy the code below and paste it on your index.html file, just after the line where you imported jQuery into the file.

<script type="text/javascript" charset="utf-8">
	var scrollSpeed = 70;
	var step = 1;
	var current = 0;
	var imageWidth = 2247;
	var headerWidth = 800;		

	var restartPosition = -(imageWidth - headerWidth);

	function scrollBg(){
		current -= step;
		if (current == restartPosition){
			current = 0;
		}

		$('#header').css("background-position",current+"px 0");
	}

	var init = setInterval("scrollBg()", scrollSpeed);
</script>

There’s nothing really hard with that code. First, we declare a set of variables to control the animation (image width, scroll speed, etc). Then, we created a function to automatically move the background. The most tricky part is to calculate when we need to reset the position. If you have a better idea about doing it, let me know in a comment! ;)

Demo & Download

I hope you enjoyed this tutorial and helps you to create very nice websites. If you want, you can see a Demo of this code, or you can Download the source files.

  • http://designinformer.com Design Informer

    Awesome tutorial! Just tweeted it.

  • http://austinpassy.com The Frosty

    Very nice little jQuery trick.

  • Pingback: Animated background image with jQuery | Webs Developer

  • http://www.wesbos.com Wes Bos

    Great tutorial Jean, this is just another step towards flash dying.

    The image doesnt get added until there is enough space for it so there is a gap every 20 seconds or so. See this screenshot:

    http://screencast.com/t/MTZiMjNkO

    Firefox 3.5

  • http://fwebde.com/ Eric B.

    Looks very cool! I would just make it move slower, to make it less distracting.

  • http://www.bebop-cafe.com BebopDesigner

    Brilliant! this looks wicked! thanks for the tut.

  • Mark

    This is sexy, for real.

  • John

    Wes – I fixed it with changing var imageWidth = 2247; to var imageWidth = 1700; but I assume you could change the headerWidth also.

    Does this have increased CPU usage because I tested it and it revved up my processor pretty good. Maybe it’s just me?

  • http://guigo.eu Guigo

    Nice tip, thanks for sharing on Twitter ;)

  • http://www.brunosabot.com Bruno

    Great, but is there very usefull to load jquery just for this animation?

    It’s really easy to use default function and speed up the execution time (while not using jquery somewhere else ofc) of the script by changing line 73 into :
    document.getElementById(‘header’).style.backgroundPosition = current+’px 0′;

    If you’re using Prototype or Mootools :
    $(‘header’).setStyle(“background-position”,current+”px 0″);

  • http://www.abonement.net Anna

    Great tutorial!

    Currentry I’m working on the same approach for one of the project – and I’ve met at least two small problems, that was not covered in your tutorial (as for myself I have not found any optimal solution for them yet)…

    1. When the cycle ends end animation restarts there is visible jump in image… When we dealing with vertiacal moving that easily could be fixed with the same pixel-set in the beginnig and in the end of animation that equal to the header height, but in the horizontal case it does not work because we don’t now the width of user’s window in this moment and this width is different for different users

    2. In your case restart position is calculated assuming that the header width is 800px, but if user has screen resolution more than 800*600 – this put you in a trouble because the user will see the end of the picture moving on the screen before the animation restarts… so there we also meet the question about user’s screen width

    probably further discussions will reveal some solutions :)
    anyway thank you a lot for sharing this code :)

  • http://www.armine.name/ Armine

    Thanks for this list :)

  • InTRUEdeR

    “var headerWidth = $(‘html’).width();” will work with any screen resolutions, but headerWidth need to be updated inside script when user resize window.

  • Pingback: Tutorial: Fondo Animado con jQuey | Recursos para Diseñadores Gráficos y Web | Creativos Online

  • http://mike.web44.net Mike

    F*%$ awesome man!!!
    I wanna implement it someday :/
    i’ll twit it right away

  • Pingback: H-Yaman » jQuery ile Hareketli Arkaplan Yapma

  • bionickid

    does NOT work. reaches the images end.

  • http://libertytuga.info/wordpress/ ORiOn

    Can you tell me if we can use the twitter background on our projects?

  • http://libertytuga.info/wordpress/ ORiOn

    By the way, you can determinate the screen resolution with: screen.width

    You just need to put it like this: var headerWidth = screen.width;

    There you go! :D

  • Pingback: Il punto della settimana #6 « Francesco Corsentino .net

  • Pingback: CHRISTMAS 2009 − Links for 2009-11-11 [del.icio.us]

  • John

    This needs to use clearInterval, doesn’t it? CPU runs to 100% the longer this runs. Anybody know how to do it?

  • http://www.traxor-designs.com/ Luke Jones

    That’s some nice jQuery!

  • Pingback: ITキヲスク | 2009å¹´11/8~11/14の週間ブックマーク

  • http://www.fantastic-replica.com jane

    i want to know if we can use the twitter background on our projects?

  • http://www.wprecipes.com Jean-Baptiste Jung

    @jane : I don’t think you can since the example image I took comes from Twitter website.

  • http://techpp.com/ Raju

    too good! loved it! love jquery!

  • Bev

    Could you please show me I would incorporate this into a wordpress site please?

  • http://charismaPlanet.com charisma

    hi don’t forget to check another inspiration at my web site click product and choose another design and after that choose my type…i have another animation for background just with jquery..i really like it..and i really like your web site name “catswhocode” ,thankyou..

  • http://cure-social-anxiety.net/ Samuel Sawyer

    Thanks for the tip. I think I’m going to use it for my site.
    I’ll modify it and embedded it in the middle of the page.

    Thanks.

  • http://teklessons.blogspot.com Anees

    Wow. Great one. I’ll definitely use this for my personal website.

  • http://http//www.no1replica.net/ vicky

    don’t think you can since the example image I took comes from Twitter website.

  • http:www.zackerymiller.com Zack

    This is pretty slick, thank you for sharing it.

    To make the animation seamless could you use two exact images that rotate positions?

    For example as image1 is halfway through it’s animation, image2 would append to the end of image1.

    When image2 moves completely into the background space, image1 would append to the end of image2.

  • Pingback: Tutorial: Fondo Animado con jQuey | Editando La Web

  • http://www.spieletipps-cheats.de Thomas

    Well done! That’s a really useful tutorial.

  • http://www.hypnosisfearofflying.com/ benedict

    I dont know much yet in jquery but this tutorial rocks!

  • Pingback: Fond animé en jQuery | Live On Design

  • http://www.denizdurumu.com Cagdas

    Woww. Thank you so much Jean.

  • http://thebestchristmaspresents.info Nic

    awesome tuts..thanks for share

  • http://reviews.cleanmyspyware.com Mike

    Awesome trick – worked for me too..

    any way to do it with a flash file ? maybe a negative z-index or something ?

  • Kapil

    Thanks alot for the neat trick. I am planning to do something similar with my personal site with some extra parameters. But this one saved me alot of coding time. :)

  • Pingback: 250 Excellent Blog Articles for Web Designers | Advertising News

  • Pingback: 250 Top Blog Articles for Web Designers | Advertising News

  • http://moralde.com/ James M.

    Wow, first time I saw an effect like this. I thought things like this are exclusive for flash websites only. I’m definitely exploring this trick. I just might incorporate it in some sites of mine. Thanks a lot.

  • http://pieterbeulque.be Pieter

    Hmm, nice start but this needs some work.

    At first I would make it go slower, which will make it less distracting. Then second, as mentioned before, it jumps when it reaches the end, so you should get the screen width and work with that value.

    Third, some people say it gets their CPU really pumped up and that’s not what we want right.

    Nice start!

  • Pingback: links for 2009-12-08 « toonz

  • http://badalyan.com Alex

    Here’s my solution for the time being:

    If you open the ‘bg-clouds.png” in Photoshop and tile the clouds to something like the width of 6741pixels and re-save it, it’s only a 100kb image still. Set the “var scrollSpeed = 70;” and you’re all set.

    Now, the kick doesn’t come in for a looooong time ;)

  • Pingback: jQuery ile Hareketli Arkaplan Yapma « Epic Network Code

  • http://cailloudesign.com Caillou

    The very cool, thanks !

  • http://affilrev.worldquests.com robert niro

    what amazing beautiful tutorial…, don’t need more flash for this animation
    Thank you so much =)

  • http://www.archetoy.com Archetoy

    Great tute, and nice code. Would love to see this with multiple depth, like parallax scrolling, so, back mid front.

    Great blog, and thanks for sharing, Digging now =)

  • chinoke

    I just want to say that Cats are really good in writing codes “art of code” after what i read in this website; Gratz

  • PaulO

    Here’s a way to get around the end of image problem:

    1. Use an image that can wrap horizontally.
    2. Add to the background style “repeat-x”.
    3. Update this line of code: “var restartPosition = -(imageWidth);”

    It’s a cool effect, but still trying to figure out if I should use it or not.

  • Pingback: Create Animated background image with jQuery | Intipadi.com

  • Pingback: 13 Great jQuery plugins you may not know about | Digital Puffin -awesomeness

  • http://mermaid-jewelry.blogspot.com/ Mermaid

    Another useful article!
    Jean-Baptiste, your whole blog is really great. Everytime I have a new idea, I keep coming back here and chances are you already covered it with a great tutorial.
    Like this one.
    Thanks.

  • dante

    Hey man, awesome tut.
    I tried to modify it so it scrolls vertically, but then IE gives me an error (I don’t care about error itself, but it wont animate in IE) in Jquery.1.4.2.js, whether it’s hosted on google or by me… weird stuff.

    here’s the code:

    var scrollSpeed = 70;
    var step = 1;
    var current = 0;
    var imageHeight = 458;
    var headerHeight = 1000;
    var restartPosition = -(imageHeight – headerHeight);
    function scrollBg(){
    current -= step;
    if (current == restartPosition){
    current = 0;
    }
    $(‘#logo3′).css(“background-position”,”0″+current+”px”);
    }
    var init = setInterval(“scrollBg()”, scrollSpeed);

    please help!! :((((

    • http://www.seeholzer.net Seeholzer

      I used the vertical image animation and it works:

      /* vertical animation */

      var scrollSpeed = 300;
      var step = 150;
      var current = 0;
      var imageHeight = 1350;
      var headerHeight = 150;

      var restartPosition = -(imageHeight);

      function scrollBg(){
      current -= step;
      if (current == restartPosition){
      current = 0;
      }

      $(‘#animation’).css(“background-position”,”0 “+current+”px”);
      }

      var init = setInterval(“scrollBg()”, scrollSpeed);

      • Eric

        How do you make the background go to the right vs. left?

  • dante

    OK NVM I did it!11

    I just copied code again and after careful analysis it seems that I had deleted empty space after zero:

    $(‘#logo3′).css(“background-position”,”0″+current+”px”);

    now it’s like:

    $(‘#logo3′).css(“background-position”,”0 “+current+”px”);

    and it works.
    I can’t believe how much SUCK IE contains, but ok.
    sorry for useless posts. :D

    great tut again, btw.

  • Pingback: Background with JQuery « LifeBits.Blog

  • http://pendiente.blogspot.com Chuck

    Wouldn’t be much easier like this?:

    function scrollBar(){
    $(‘#header’).css(“background-position”,”0px 0px”).animate({backgroundPosition: “-2247px 0px”},4000,”linear”,scrollBar);
    }

    $(function(){
    scrollBar();
    });

    :)

  • http://pendiente.blogspot.com Chuck

    Also, changing the background repeat to just “repeat” for it to repeat horizontaly as well.

    Cheers

  • http://www.endowmax-review.com Rob

    This is very inspiring. I’m learning a lot and realize just how far I have to go!

  • http://www.youtube.com/watch?v=x5fWPcmo6uk Jamie

    Another great tutorial. I like the Twitter background. I previewed the demo and it was great. Looking forward to some more tutorials from you.

  • http://www.agencia110.com.br Le

    Hi there,

    Nice code!

    Some changes to continuous move.

    var imageWidth = 2247; // Background image width
    var headerWidth = 1685; // How wide the header is.

    I Hope helped someone

    Bye

  • http://sahuspilwal.com Sahus Pilwal

    Nice trick!!! Unfortunately the demo links are broken or not found…

  • http://tylerherman.com Tyler Herman

    Would like to see the demo, the link is still broken.

  • http://bloggingdotnet.blogspot.com james westgate

    Two immediate problems here:

    1. Just use jQuery animation so that your animation fits in with other animations running on the page,

    2. If you do use your own timer, dont pass a string to setInterval, use an anonymous function instead eg

    function() {scrollBg()};

    This will improve performance.

  • http://www.vizyweb.com.au/ Robin

    Love your work on that code

  • David Zapata

    Your online demo link is broken.

  • y0y0

    Thanks for the code!

    Quick question: Is there a way to do this without the global variables? I’d rather make them all local and neat.

  • y0y0

    nm, I figured it out.

    :)

  • Mr Gibons

    Hey, I am trying to expand the content section so it expands to 100% of the height but, if I do this the box disappears. Any help?

  • http://sotiriskalathas.gr/ Sotiris Kalathas

    A little improvement to your awesome script:

    No need for var headerWidth just use $(“#header”).width() or $(window).width() instead, any will do!

    I also changed the script to scroll the other way!

    Enjoy:

    var scrollSpeed = 1; // Speed in milliseconds
    var step = -1; // How many pixels to move per step
    var current = 0; // The current pixel row
    var imageWidth = 2247; // Background image width

    //The pixel row where to start a new loop
    var restartPosition = -(imageWidth – $(window).width());

    function scrollBg(){
    //Go to next pixel row.
    current += step;

    //If at the end of the image, then go to the top.
    if (current == restartPosition){

    current = 0;
    }

    //Set the CSS of the header.
    $(‘#header’).css(“background-position”,current+”px 0″);
    }

    //Calls the scrolling function repeatedly
    var init = setInterval(“scrollBg()”, scrollSpeed);

  • Matt

    Demo appears to be unavailable now?

  • Tobias Beuving

    For me the demo also does not work – the links to it take me to a 404 page…

  • Lucas

    I could not make it scroll vertically, even with the examples here posted, do i have to change something in the CSS? please who ever knows, post the full code! thanks!

  • ArthurD

    So many people are confusing the issue with the header repeating. The point of repeat has nothing to do with the actual width of the header, but the point that the pattern repeats. So for example if you have a pattern repeats after 100 pixels then you subtract that from the total width of the background pattern. So if the image width were 2000, then this is what the two values would be:

    var imageWidth = 2000;
    var headerWidth =1900;

    now if your image doesn’t repeat for the entire length of the image then all you would have to do is set the variableas as follows:

    var imageWidth = 2000;
    var headerWidth =0;

    With repeat-x turned on the image will blend seamlessly with it self. Of course there are other methods of achieving what’s being done here, but this is how you get the background to repeat using this code.

  • dean

    somthing missing????????????

    //The pixel row where to start a new loop
    var restartPosition = -(imageWidth – $(window).width());

  • http://www.adesignguy.co.uk chris

    Very good trick, but not complete.. How do you clear the memory and reset the image on one successful scroll because if you start taskmanager you can see the cpu usage going up and up and up the longer you leave the loop going?

  • http://www.travellerkids.com Shitij

    Awesome…..thanks for this….trying to put it inside wordpress for an animated backgorund for random flying objects

  • http://drawne.com Andy Feliciotti

    just an fyi your demo is broken

  • Dominor Novus

    Thanks for the tutorial but a working demo would be useful.

  • Friday13

    Here is similar working example: http://jquerydemo.com/demo/animate-background-image.aspx

  • http://www.explanimate.com.au/ Joy Brooki

    Thanks for this update. Is it compatible to all browsers? If it is so, I will definitely give a try. Thumbs up for your work..!