0

This is a function used to detect VML support in browsers. It's part of an html component file for giving border-radius and drop-shadow functionality to older versions of IE. I would like this explained to me, the step-by-step logic of it:

function supportsVml() {
    if (typeof supportsVml.supported == "undefined"){
        var a = document.body.appendChild(document.createElement('div'));
        a.innerHTML = '<v:shape id="vml_flag1" adj="1" />';
        var b = a.firstChild;
        b.style.behavior = "url(#default#VML)";
        supportsVml.supported = b ? typeof b.adj == "object": true;
        a.parentNode.removeChild(a);
    }

    return supportsVml.supported
}

Where I am confused:

  1. What is supporstVml.supported? Is this a variable, I don't see it declared anywhere else int he file...
  2. what is the url(#default#VML) behavior?
  3. supportsVml.supported is reassigned a new value based on the conditional, but I have no idea what or why...

Thanks!

Seth Flowers
  • 8,990
  • 2
  • 29
  • 42
Jeff Fabiny
  • 325
  • 2
  • 15
  • That's some not-so-good code there, whatever it does. Where did it come from? – Pointy Aug 21 '12 at 13:40
  • @Pointy All over the place lol, http://tobymackenzie.wordpress.com/2010/07/06/css-ie-shadows-and-rounded-corners/ , http://stackoverflow.com/questions/654112/how-do-you-detect-support-for-vml-or-svg-in-a-browser This is code I have to work around, not change. So I'm not interested in optimizing it or changing it, just understanding it. Thanks again! – Jeff Fabiny Aug 21 '12 at 13:43
  • Well it's bad because it just is. That "b" variable is assigned and its value is assumed to be non-null **before** the test is made in the subsequent line. That is, if `a.firstChild` is null, then the assignment to `b.style.behavior` will throw an exception. If it's not `null` then the test made for the `? :` expression is pointless. – Pointy Aug 21 '12 at 13:46

1 Answers1

2

supportsVml.supported is a property of the function, which is used just as a caching for the result.

If it is undefined (before the first call), the detection algorithm is run. Afterwards just the cached value is used and the detection is omitted.

The actual detection algorithm tries to add a default VML element and checks, whether this is inserted correctly. If so, VML is supported.

EDIT

The behavior can attach scripts to the CSS of an element (link). As far as I know, this is unique to older IE versions.

supportsVml.supported = b ? typeof b.adj == "object": true;

This line uses a ternary operator. It could be rewritten as follows:

if ( b ) {
  if ( b.adj == 'object' ) {
    supportsVml.supported = true;
  } else { 
    supportsVml.supported = false;
  }
} else {
  supportsVml.supported = true;
}
Sirko
  • 72,589
  • 19
  • 149
  • 183
  • Thanks for clearing up my first question! Can you tell me what role the behavior plays? Or the conditional statement? I get the VML insert, but these other two are new to me. – Jeff Fabiny Aug 21 '12 at 13:49