是否有跨浏览器和跨框架方式来检查对象是否是HTML元素?

时间:2013-12-11 18:06:05

标签: javascript html dom cross-browser

给定一个对象obj,我想检查该对象是否是本机HTML元素。我能做到:

if ( obj instanceof HTMLElement )

但是这不适用于帧(例如,来自<iframe>的对象),因为每个帧都有自己的HTMLElement构造函数。或者,我可以这样做:

if ( obj.tagName ) 

但这不安全/可靠,因为这样的属性可以(非)故意添加到对象中。

那么,有可靠的方法吗?

4 个答案:

答案 0 :(得分:2)

您可以使用以下内容,接受这样的事实:这仅适用于支持HTMLElement作为基本构造函数的UA:

/// testing vars
var localBody = document.body;
var foreignBody = document.getElementById('iframe').contentDocument.body;

/// useful function
var deriveWindow = function( elm ){
    return elm && 
        elm.ownerDocument && 
        (elm.ownerDocument.defaultView || 
        elm.ownerDocument.parentWindow)
    ;
};

/// instanceofs
console.log( localBody instanceof HTMLElement );
console.log( foreignBody instanceof HTMLElement );
console.log( localBody instanceof deriveWindow(localBody).HTMLElement );
console.log( foreignBody instanceof deriveWindow(foreignBody).HTMLElement );

输出因浏览器而异,Firefox 25(在Windows 7上)给出:

true
true
true
true

IE 11,Opera 12,Safari 5和Chrome 31(在Windows 7上)都给出了:

true
false
true
true

小提琴:

答案 1 :(得分:0)

最好的方法我知道如何检查对象的toString表示。

HTMLElement的字符串表示总是有两件事情:

  1. 它将以[object HTML
  2. 开头
  3. Element]
  4. 结尾

    这里有详细的检查方法:

    var str = Object.prototype.toString.call(obj),
        isHtmlElement = str.indexOf('[object HTML') === 0 
                     && str.indexOf('Element]') > -1;
    

    还有一些(但很小的)误报的可能性。

答案 2 :(得分:0)

您可以使用nodeType和nodeName属性,但遗憾的是,如果将这些属性添加到非HTML元素对象中,您仍会遇到问题。

http://www.w3schools.com/dom/dom_nodetype.asp

//Returns true if it is a DOM element    
function isElement(o){
    if (typeof o === "object" && o.nodeType === 1 && typeof o.nodeName==="string") {
        return true;
    } 
    return false;    
 }

答案 3 :(得分:0)

isPrototypeOf功能怎么样?对于任何HTML元素,HTMLElement.prototype.isPrototypeOf(obj)都应该返回true,而对于某个随机对象,false应该返回。{/ p>

我没有机会跨框架测试它,所以我唯一担心的是它是否会遇到instanceOf所遇到的同一问题。 。