开发者

ExtJs4 + IE9 = Object doesn't support property or method 'createContextualFragment'

I'm working with ExtJs on IE9.. and i almost always get this error..

Microsoft JScript runtime error:

Object doesn't support property or method 'createContextualFragment'

What dose it means? What 'createContextualFr开发者_开发百科agment' is needed for? And how to fix this?


createContextualFragment() is a method of Range objects that creates a document fragment from an HTML string. It's present in Firefox and WebKit and Opera but is currently non-standard (it's not in the DOM Level 2 Range spec but is in the work-in-progress DOM Parsing and Serialization spec) and IE 9 didn't implement it, which is consistent with Microsoft's general approach to implementing standard functionality in IE 9 that was previously missing in IE. ExtJs must be using this method, although rather foolishly since it is non-standard and the same result can easily be achieved using innerHTML, which is supported everywhere.

UPDATE

You can patch the following into IE 9 since it allows extension of host object prototypes, which previous versions did not. The following is a naive implementation of createContextualFragment() adapted from my Rangy library but is suitable for most uses. See this Rangy issue for details and for a more thorough implementation.

Note that this will not work in IE < 9 because those browsers have no DOM Range implementation.

if (typeof Range.prototype.createContextualFragment == "undefined") {
    Range.prototype.createContextualFragment = function(html) {
        var startNode = this.startContainer;
        var doc = startNode.nodeType == 9 ? startNode : startNode.ownerDocument;
        var container = doc.createElement("div");
        container.innerHTML = html;
        var frag = doc.createDocumentFragment(), n;
        while ( (n = container.firstChild) ) {
            frag.appendChild(n);
        }
        return frag;
    };
}


Faster, tighter, no looping, works in IE9+ and all non-shit browsers:

var createContextualFragment = (function(){
  var doc = document.implementation.createHTMLDocument(''),
      range = doc.createRange(),
      body = doc.body;
  return function(html){
    body.innerHTML = html;
    range.selectNodeContents(body);
    return range.extractContents();
  }
})();


Well, with a small change, the code posted by Tim Down worked for me :

if (typeof Range.prototype.createContextualFragment == "undefined") {
    Range.prototype.createContextualFragment = function (html) {
        var doc = window.document;
        var container = doc.createElement("div");
        container.innerHTML = html;
        var frag = doc.createDocumentFragment(), n;
        while ((n = container.firstChild)) {
            frag.appendChild(n);
        }
        return frag;
    };
}


extjs 3.4.0 fixes this issue. No need to change the code bade. Good work on the library, though.


This has already been fixed in Ext JS 3.3 IIRC, and I imagine it will be fixed in 4.0 prior to the final release (it hasn't even hit beta as of this writing).


I've just applied Tim Down's fix to our ext 3.3.1 installation, because IE9 still doesn't display our pages correctly without it. In other words, I don't think this fix got into EXTJS 3.3, at least not the public version.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜