Tuesday, December 1st, 2009

Star Wars HTML and CSS: A NEW HOPE

Category: CSS, Examples, WebKit

There are a lot of CSS transitions experiments going on right now. Yesterday I discovered another HTML and CSS experiment which went “far far away“, compared with my simple CSS gallery.

Guillermo Esteves presented a piece of history translated for tomorrows browsers:  the Star Wars Episode IV opening crawl in HTML and CSS:

Unfortunately, the live experiment is not suitable for all browsers and the ideal target seems to be only OSX 10.6 and its latest Safari browser but it partially worked via Google Chrome as well.

Something To Learn About

We are moving complex computations into our favorite “decoration layer”: CSS
We also want as much control as possible, and the above concept is brilliant to understand how to tame CSS transitions.
This example includes new and different techniques. Here is what I found interesting:


OK, this is not new at all, but in this case I could not find a single valid reason to avoid the original font: a must! The only point here is that the author could have saved a bit of bandwidth via pre-deflated or gzipped fonts rather than serving them without any apparent optimization.

  1. @font-face {
  2.    font-family: FGB;
  3.    src: url("/experiments/frabk.ttf") format("truetype");
  4. }

It’s a shame there is not the real STAR WARS font as well but just an image … anyway, let’s move into more concrete stuff …


  1. #stage {
  2.   height:600px;
  3.   width:1000px;
  4.   overflow:hidden;
  5.   margin: 0 auto;
  6.   -webkit-perspective:800;
  7.   -webkit-perspective-origin:center 300px;
  8. }

The stage is the block element where the magic happens. The perspective property is able to give us a “deep space” 3D feeling making closer objects look larger than further ones. Via origin modification we can decide where things should disappear, in this case a bit higher point than a central 400px, to create a similar atmosphere respecting the movie choice (and I guess to make content readable as well).

Iteration-count and Custom transitions

  1. #far-far-away {
  2.   color:rgb(75,213,238);
  3.   font-family:FGB, sans-serif;
  4.   font-size:48px;
  5.   line-height:1.5;
  6.   position:absolute;
  7.   top:200px;
  8.   left:190px;
  9.   opacity:0;
  10.   -webkit-animation:fade-in-out 6s linear;
  11.   -webkit-animation-iteration-count: 1;
  12.   -webkit-animation-delay:5s;
  13. }

Far far away is the initial text. As we can see with other browsers as well this appears and disappear in 6 seconds.
This fade-in-out happens just once, so at the end of the effect, unless we won’t modify the node class, the element won’t be displayed anymore. This is what the animation-iteration-count property does while next snippet is the fade-in-out customization:

  1. @-webkit-keyframes fade-in-out {
  2.   0% { opacity:0; }
  3.   16%   { opacity:1; }
  4.   84%   { opacity:1; }
  5.   100%   { opacity:0; }
  6. }

Via keyframes <transition_name> we can blend FX linearity deciding the amount of opacity, or other properties, at certain moments.
A generic normal linear fade-in-out would be visible 100% only in the middle of the transition while in this case it is forced to be visible for 68% of the time, making fade in and out still homogeneous but controlling the full opacity for longer.
We could have used an ease-in-out effect over opacity property to obtain a similar result but I find definitively more interesting this kind of approach.

Warp Speed: Action!

Thanks to Z axis transitions the initial STAR WARS image can appear and disappear using again a customized FX:

  1. @-webkit-keyframes logo {
  2.   0% { -webkit-transform: translateZ(0); opacity:1;}
  3.   50% { -webkit-transform: translateZ(-50000px); opacity:1; }
  4.   60% { -webkit-transform: translateZ(-60000px); opacity:0; }
  5.   100%   { -webkit-transform: translateZ(-100000px); opacity:0;}
  6. }
  8. /* few lines after, img is the only logo image */
  9. img {
  10.   opacity:0;
  11.   position:absolute;
  12.   top:100px;
  13.   width:1000px;
  14.   -webkit-transform-origin:center center;
  15.   /* above custom logo animation */
  16.   -webkit-animation:logo 25s linear;
  17.   -webkit-animation-iteration-count: 1;
  18.   /* suspance before the logo ... */
  19.   -webkit-animation-delay: 12s;
  20.   /* logo appears slower and fly away faster */
  21.   -webkit-animation-timing-function: ease-in;
  22. }

Above mix of webkit properties suggests me that new JavaScript libraries will use run-time actions to CSS transformations soon, rather than hard and manual JS computations over computed styles or similar expensive operations.
We can control delays, we can stop FXs removing classes or simply overwriting existent directives and, moreover, we can split the CSS itself into logical parts as the same @gesteves did, putting custom animations all together: good hint!

The Crawl

Last piece to check out is the text plus its title.

  1. /* custom crawl FX */
  2. @-webkit-keyframes crawl {
  3.   /* axis management until it disappears */
  4.   0% { -webkit-transform:rotateX(80deg) translateZ(300px) translateY(1100px);opacity:1;}
  5.   40% { -webkit-transform:rotateX(80deg) translateZ(300px) translateY(-340px);opacity:1;}
  6.   80% { -webkit-transform:rotateX(80deg) translateZ(300px) translateY(-1780px);opacity:0;}
  7.   100% { -webkit-transform:rotateX(80deg) translateZ(300px) translateY(-2500px);opacity:0;}
  8. }
  10. #crawl {
  11.   color:rgb(252,223,43);
  12.   font-family:FGD, sans-serif;
  13.   text-align:center;
  14.   font-size:36px;
  15.   opacity:0;
  16.   /* long animation */
  17.   -webkit-animation:crawl 120s linear;
  18.   /* again just once */
  19.   -webkit-animation-iteration-count: 1;
  20.   /* starting while the logo is still there */
  21.   -webkit-animation-delay:16s;
  22.   /* preserving 3D aspect for the entire animation */
  23.   -webkit-transform-style:preserve-3d;
  24. }
  26. #crawl p.title {
  27.   font-family:FGDC, sans-serif;
  28.   /* it's a title */
  29.   text-transform:uppercase;
  30.   /* it's massive */
  31.   font-size:96px;
  32.   /* but scaled to fit inside margins */
  33.   -webkit-transform:scaleX(0.6);
  34. }
  36. #crawl p {
  37.   /* preserve spaces */
  38.   white-space:pre;
  39. }

The Mythical Song

Well, this demo could not miss a proper audio element:

  1. <audio src="/experiments/starwars.m4a" id="audio" autobuffer="autobuffer" />

Apparently the used compression is truly good and the sound loud and clear. But who is in charge to start above song?


Quite hilarious all this demo does not basically need JavaScript at all except for an audio delay forced via interval:


  1. setTimeout("document.getElementById('audio').play()", 12000);

If we have a good broadband connection and we are sure in 12 seconds we have buffered enough audio, the synchronization between JavaScript and the transition delay is almost perfect and the demo experience unique.

It is great to see this work, and I look forward to seeing what he comes up with next. It feels that with HTML5, CSS3, and the Web.Next we will be able to be much more creative. Finally, it’s December, I can already imagine a CSS3 based snow effect for our pages … no?

Posted by webreflection at 7:00 am

3.9 rating from 68 votes


Comments feed TrackBack URI

Interestingly enough, you can do the same thing in Internet Explorer 5.5+ by using HTML+Time with CSS filters. No JavaScript needed at all, not even for the audio delay.

Comment by TNO — December 1, 2009

Thanks a lot for the writeup! You certainly explained it better than I would have.

Comment by gesteves — December 1, 2009

By the way, if anyone knows the precise technical reason why these 3D transforms only work in Snow Leopard, I’d love to know. I’m thinking they’re done using some 10.6-specific Core Animation/Core Image functions, but I’m not knowledgeable enough about the internals of OS X to know for sure.

Comment by gesteves — December 1, 2009

Actually gesteves, I’m not convinced it’s a Snow Leopard thing considering the demo works great in the latest version of WebKit on my OSX 10.5 machine. So maybe the 10.5 version of Safari just uses a different version of WebKit than the 10.6 version?

Comment by danlucas — December 1, 2009

I have to say, this is extremely cool. I wish Firefox would catch up with webkit in terms of CSS animations, 3d transforms, etc., support. I’ve been working on a website specifically targeting iphone and the ability to do so much “fancy stuff” without ever touching JS is… well, liberating :)

Comment by iliad — December 1, 2009

Hmm, it’s possible, I didn’t try it in the nightly on my 10.5 machine, only the stock Safari and it came out all wrong. In any case, hopefully these new features will come to the rest of the WebKit-based browsers soon enough.

Comment by gesteves — December 1, 2009

Bah… Where’s the rest of the movie??
Hope to see these features trickle down into the other browsers soon.

Comment by rasmusfl0e — December 1, 2009

I know iliad! I made a timer thing using only CSS transforms and animations (and no JavaScript) and I was pleasantly surprised to see that it worked perfectly on the iPhone. You can try it out at http://www.gesteves.com/experiments/timer.html

(I also made a more standard clock that does use JavaScript at http://www.gesteves.com/experiments/clock.html )

Comment by gesteves — December 1, 2009

@TNO – Nice! It looks like Safari has almost caught up with IE 5.5.

Comment by WillPeavy — December 1, 2009

Don’t have my Mac the office, and Chrome is only “ok” at rendering … but, it works on the iPhone!

Comment by arougthopher — December 1, 2009

div+css battery website: http://www.electric-power.us

Comment by holy2050 — December 3, 2009

i love star wars

Comment by Aphrodisiac — January 15, 2010

Leave a comment

You must be logged in to post a comment.