A modern approach to Flash SEO

Search engine optimization is one of the most popular subjects when nerds sit around and talk about Flash. “Does Google index your swf files?” seems to be the most popular question, usually garnering plenty of ‘yes‘ and ‘no’ and ‘maybe’ answers. The real answer to this question, once and for all, is this:

It doesn’t matter.

To understand this answer, you need to understand what Flash is. And to do that, you need to understand modern web development philosophy. First off, you need to embrace web standards. Semantic markup and separating content from style and behavior is the only way you should be building your sites. Many web standardistas have been recommending this method of web development for years, and rightly so. However, this post isn’t the place to go into the whys of this type of development, so I’ll skip that part and just say this about how it’s done: There are three areas of front-end web development: Content, Style, and Behavior. You should always keep these three things separated as much as possible.

That brings up the question: “Where does Flash fit into this three pillar method of web development?” Is it content? Is it behavior? Is it style? While it could be considered all three, most professional Flash developers will remove the content from their Flash movies and load it in using Flash remoting or XML files. That leaves us with style and behavior.

Style is added using CSS. Generally when you add images to your HTML that are purely presentational (no text or required content in them) you should add them in using CSS. In most cases you don’t want Google to index them because people don’t search the web for ‘top left rounded corner gif.” They search for content. Even if Google upgrades their crawler someday to read CSS files and index the images, they probably wouldn’t use the information for more than statistical analysis because of this.

Behavior is generally added using Javascript. Maybe you want a new window to open set to a certain size, or you want to use some fancy Ajax to let users rate something without refreshing the page. This should all be added unobtrusively, and if the browser doesn’t support Javascript, it will hopefully still work. Unfortunately, not everyone considers this, and these days Javascript is becoming more and more of a requirement to use most websites. So you should always provide some sort of alternative for non-Javascript users. When it comes to indexing behavior, Google will for the most part not index your Javascript files. Even if it did, most web users would have no idea what the .js file they are looking at actually does. When using Javascript to change your document, Google will not read the ‘final’ page, but only the raw HTML file. Google does not render Javascript 1.

Now that you know all of this, it’s time to look at how to treat your Flash content. Since we’ve determined we don’t want Google to index our swf files, but we do want it to index the content displayed inside them, what is the best way to go about this?

As stated before, if you are building Flash sites professionally, you probably move all your content out of your Flash movie and into an XML file or keep it in a database. This makes it much easier to allow Google to index this content by using progressive enhancement.

Progressive enhancement is a method of web development that goes hand in hand with Web Standards. You start with your HTML (your content), then add CSS (your look and feel), then add in additional behavior (Javascript, Ajax, Flash, any other interactivity that isn’t handled automatically by the browser).

The best way to add Flash progressively is by using Javascript, or more specifically, a script like FlashObject. First you lay out your page as if you aren’t using Flash. If you are using a database for your content, you can spit out that data as HTML where the Flash movie will go on the page (or maybe just a preview of the content, it’s up to you to show Google the content you would like indexed). Then you use FlashObject to replace this content only if the user has Javascript enabled and the required Flash plugin version.

Here’s a small example of what that might look like:

<div id="flashcontent">
    This is replaced by the Flash content if the user has the correct version of the Flash plugin installed.
    Place your HTML content in here and Google will index it just as it would normal HTML content (because it is HTML content!)
    Use HTML, embed images, anything you would normally place on an HTML page is fine.
</div>
<script type="text/javascript">
    // <![CDATA[
    var fo = new FlashObject("flashmovie.swf", "flashmovie", "300", "300", "8", "#FF6600");
    fo.write("flashcontent");
    // ]]>
</script>

This causes Google to skip the Flash swf files and only index the HTML (the content!) you place on the page. You can place links to other pages, images, whatever you want Google to index, and when a viewer with a browser that supports Flash visits your site, they will then see the Flash content. This gives you full control and much greater predictability over what content Google will index. And if your content is pulled from a database that is editor controlled, your pages will update and be re-indexed as the content changes without the need to re-publish all your swf files.

1 Currently Google does not render the Javascript on a page, but there are rumors that they are developing a new crawler based on Firefox (they employ a number of Mozilla foundation members) that will index pages based on how the browser sees them, instead of the raw HTML content. This means HTML hidden by CSS may not be indexed, and pages that are altered by Javascript after they load will be indexed how they appear to the user. However, this is all rumors and until it happens Google will ignore your Javascript content.

Note: In this article I use the ‘Google’ name often, but it can be interchanged with any search engine, as they all work roughly the same way.

FlashObject 1.3 Released

I have just released version 1.3 of FlashObject. Changes are as follows:

  • [Changed] When calling FlashObject.write() you can now pass an HTMLElement reference. Previously you needed to pass a string (the Id of the element to write the Flash content to)
  • [Changed] Made changes to the plugin detection routine that would cause a crash in browsers running certain versions of the Flash plugin. Read a comprehensive description of the issue and the fix.
  • [New] You may now specify a specific URL to redirect the user to after they complete an ExpressInstall process. Previously the script would always redirect them to the page the Flash movie was embedded in, but when using a popup window this is not always the best solution. See the ExpressInstall section of the FlashObject page for more information.
  • [New] FlashObject now integrates seamlessly with the Javascript Integration Kit. More information on this is forthcoming in a new blog post.
  • [New] I’ve used Dojo Shrinksafe to strip out the extra space in the flashobject.js file. FlashObject now weighs in at just a hair over 6kb. Super tiny! The FlashObject ‘source code’ (un-shunken Javascript) is included in the FlashObject zip file in the ‘source’ folder. I also made a number of small syntax changes to reduce the size even more.

I’ve updated the FlashObject page to reflect these changes. I recommend that everyone should upgrade if you are using any older version of FlashObject. If you are upgrading from v. 1.2, you can simply replace your flashobject.js file and you should be ready to go. Versions earlier than 1.2, you may need to make minor adjustments to your embed code (see the changes to v. 1.2 for help with that)

UPDATE (1-25-2006): Found a small bug in this latest version that caused the Flash movie to not load on IE 5.01 on PC. The bug has been fixed and the zip/source has been updated. Please update to the latest version if you are using 1.3 and have a lot of users using IE 5.01 (does anyone have a high number of those anymore?). The new version number is 1.3b.

The new Macromedia Flash Player detection kit

With the announcement of Flash 8 today, Macromedia also quietly pushed out their new detection kit. The detection kit has has been around for the last few versions of Flash, and usually changes with each version to include whatever the latest trends in Flash detection are.

It’s no wonder then, that the latest version uses Javascript as the suggested detection method. Unfortuntely, it’s not perfect. While it’s a good first try, it is greatly lacking in a few basic needs of most web developers. Here’s the issues I have with it:

  • Inline Javascript code (and lots of it) – Who wants to copy a bunch of Javascript and VBscript onto every single page that uses Flash? While it might be possible to move the Javascript into an external file, you would still have a small amount of VBScript on each page (or another external file to include). I’m not sure why they decided to leave in the VBScript when there are other reliable ways to create and test for ActiveX objects. Also: what happens if you need to upgrade the Javascript for some reason? While the code should be very futureproof, you never know when a bug might pop up, and you’ll be stuck editing all of your HTML files that have Flash movies included in them.
  • Tough to modify the code – It suffers from the same drawbacks as most Javascript embed techniques – placing tons of Javascript document.write() calls and writing out your object or embed tags to the page. This is a hassle to edit if you need to make changes, and makes it very tough for designers who don’t know Javascript to go in and modify attributes.
  • It’s not valid HTML or XHTML – Valid XHTML documents aren’t for everyone, but when you have clients specifically asking for them it’s nice to be able to deliver. The new detection doesn’t even come close to validating.

If you want to compare the new Macromedia detection to my FlashObject script, check out this new article that shows how to use it:

Best Practices for Flash Player Detection

Then compare the steps needed to get that working with using FlashObject:

  1. Include single .js file.
  2. Add a few lines of code (see example of bare minimum).
  3. Sit back, relax.

I think the choice is clear.

Now when you downloaded the new detection kit you may have noticed another folder hiding out in there with the name of “Express Installation.” This is Macrmedia’s new way of upgrading your Flash player without the need to go to macromedia and download the new plugin. I’ll be writing up a new entry soon that gives some tips and best practices on using this method in the very near future.

FlashObject 1.2

I’m pleased to announce version 1.2 of my FlashObject script. The big new addition is minor version detection and revision detection, so now you can detect versions like "6.0.65" if you like. I also got some advice from Toby Boudreaux, who provided tons of help in getting the code all fancied up and name spaced, so it shouldn’t collide with any other scripts on your websites now. We also went through and leaned out some features that weren’t being used much. Namely the fo.altTxt var and the extra line that included the bypass detection link. You can still bypass the detection just as you have been, but the script will no longer automatically write the alternate content at all (even if you manually override it like you could in v.1.1). If you have no idea what that last sentance means, just ignore it, as you probably weren’t using the feature anyway.

I’ve also given FlashObject a permanent home at http://blog.deconcept.com/flashobject/.

Here’s the full list of what has changed:

  • fo.write() now requires an element ID. In previous versions you could call write() with no parameters and the FlashObject script would write the Flash movie to the page wherever the script was placed on the page. This is no longer the case and now you must specify an element ID.
  • fo.altTxt no longer exists. You must now place all your alternate content or upgrade message in the div where your Flash content will be written.
  • fo.redirect no longer exists. When using FlashObject to redirect users to a separate upgrade page, you now specify the redirect url like this: fo.setAttribute('redirectUrl', 'http://www.example.com');

I highly recommend upgrading to this version. While I was adding the minor version detection, I found a bug that will cause Netscape plugin based browsers to fail the Flash detection once the major version gets up to two digits. That means it will work fine up to Flash 9, but then return 0 if the user has Flash player 10 (this is all assuming Macromedia keeps incrementing the version numbers, and that Adobe doesn’t change everything around when they take over).

So that’s it. This will probably be the last version update to FlashObject, since there isn’t much else I could add that would be useful to everyone. So go tell your friends about it – there’s really no reason you shouldn’t be using this to embed your Flash movies.

UPDATE: Dave Benjamin pointed out a flaw in the new detection checking function, and that has been fixed. I also fixed a very small issue with the version check that would cause it to fail if you had version 9.1.0, and the page required 8.2.0 (for example), so make sure you get the latest version.

UPDATE (07-27-2005): Matthew Richmond set me up with a better looking test file, that also shows the full page version much better, so the download / example pages have been updated.

UPDATE (08-01-2005): Just fixed a bug in the detection function that would throw an error when no Flash player was installed, thus casing the redirect to fail if you were trying to redirect users to an upgrade page. Thanks to Carl Wurtz for pointing that out. I also took the chance to update the ActiveX plugin detection code. No more VBscript in there (not even an execscript() call). New version number is 1.2.2 – make sure you have the latest version!