CBono
CBono

Reputation: 3803

IE8 / JavaScript: Override native implementation of document.all.item?

I know this is crazy, but IE can drive one to do crazy things.

Here's the deal: we have a SharePoint 2007 site with Content Editor Web Parts. We have a contingent of users with Internet Explorer 8. We want to keep the site in IE8/IE8 Standards modes for better rendering of content. However, this configuration breaks the ability to open the Rich Text Editor window from the C.E. web part.

If we force IE8 into IE7 document mode or quirks mode, it works. Indeed, other sources online have suggested doing just that to fix the problem. But we'd really rather have everything run in standards mode.

Through some debugging, we found the source of the problem to be the use of document.all.index("<web_part_id>") JavaScript when retrieving a web part object on the page. In IE8 standards, this returns an object with most of the properties either empty, null or undefined; most notably, the id property is not set. If you were to use document.getElementById to retrieve the same ID, you get back a fully populated object. Likewise if IE8 is not in standards mode, you get back a mostly (but not completely) populated object -- but populated enough to avoid the script error, anyway.

All this code looks like it is injected dynamically into the SharePoint page, so that rules out simply replacing references to document.all. However, we got the crazy idea of redefining the document.all.item method to actually invoke document.getElementById. Our attempts so far to do this don't work, so perhaps someone might shed some light on what we're doing wrong (okay, there's lots wrong about this, but it's IE and SharePoint, right?).

Our initial attempt at an override looks like this:

<script type="text/javascript">
    document.all.item = function(id) { return document.getElementById(id); }
</script>

This code is in the document HEAD, above any other script references (SharePoint or otherwise), but it does not appear to supersede the native code.

Thoughts, ideas, suggestions and criticisms welcome!

Upvotes: 1

Views: 2121

Answers (2)

Dr.Molle
Dr.Molle

Reputation: 117354

document.all is a HTMLCollection, so you may use HTMLCollection.prototype to change the behaviour:

if(document.all 
   && !window.opera 
    && typeof HTMLDocument=='object' 
     && typeof HTMLCollection=='object')//filter IE8
{
  HTMLCollection.prototype.item=
  function(id)
  {
   return((this==document.all)
           ? document.getElementById(id)//document.all
           : this[id]//maintain native behaviour for other collections
         ); 
  }
}

Upvotes: 3

AsherMaximum
AsherMaximum

Reputation: 972

So you're saying you can't change the references to document.all.item because SP directly injects it to the html? So couldn't you use the DOM to replace it?

BTW, I feel your SharePoint pain. I've built SP workflows, and those are enough of a pain for me!

Upvotes: 0

Related Questions