document.createElement不起作用
我正在使用jQuery库创建一个插件。
这里我将String.prototype存储在变量中,然后我使用此变量来扩展我的Sting对象。 这工作正常。
// String Prototyping store in a variable // Save bytes in the minified version of js var StrProto = String.prototype; String.prototype.toProperCase = function () { return this.replace(/\w\S*/g, function (txt) { return txt.charAt(0).toUpperCase() + txt.substr(1).toLowerCase(); }); }; // working fine alert("yogesh kumar".toProperCase());
在下一种情况下,我正在创建存储在abc变量中的m 函数xyz ,这也正常工作。
function xyz(x){ alert(x) } var abc = xyz; // working fine abc("yogesh kumar");
在最后一种情况下,我将document.createElement存储在变量标签中,并使用标签创建一个按钮。 但这不起作用。
var tag=document.createElement; $(document.createElement("button")).html("document.Element").appendTo("#myDiv"); // not working $(tag("button")).html("tag").appendTo("#myDiv");
请检查jsFiddle上的链接:
点击这里
错误:
在Chrome中
- 未捕获的TypeError:非法调用
在Firefox中
- 错误:NS_ERROR_XPC_BAD_CONVERT_JS:无法转换JavaScript参数
为什么这个错误?
解决办法是什么?
您将获得对作为文档成员的函数的引用。 当您直接调用该引用时,它的上下文现在是窗口而不是文档。 这是一个例子:
var foo = { createElement: function(tagname) { if (this._secretvarthatisneeded) { console.log(tagname + " Element Created!"); } }, _secretvarthatisneeded: true } foo.createElement("FOOBAR"); // works var bar = foo.createElement; bar("BARFOO"); // doesn't work bar.call(foo,"BARBAR") // works
由于上下文丢失, bar()
调用没有导致console.log();
显然,这只是一个简化演示。
更新:对于您正在使用的用途,我建议这样做:
$.createElement = function(tagName,attributes){ return $( document.createElement(tagName), attributes ? attributes : {} ) }
现在你可以简单地做$.createElement("button").html("tag").appendTo("#myDiv");
它速度快且易于阅读。 但请注意,IE输入有问题,如果你正在创建输入元素,我建议使用$("")
而不是这个。
jQuery可以为您创建新元素 ,如下所示:
$("").html("document.Element").appendTo("#myDiv");
要了解您的方法无效的原因,请阅读@ Kevin的评论如下。
使用bind()
方法将本机JS方法“赋值”给变量:
var ce = document.createElement.bind(document); var elem = ce('div'); alert(elem.nodeName);
适用于现代浏览器,包括IE9 +。 对于旧版浏览器,请使用包装函数。
这种情况正在发生,因为document.createElement
本身就使用了它。 当你像document.createElement()
一样调用它时,它被设置为document
。 但是,当您将其保存为变量时, this
不再是document
,而是window
。
您需要使用上下文调用它。
var tag = document.createElement; // you are saving the function, not its context var btn = tag.call(document, 'button'); // you need to set the context
如果您的浏览器支持它,您也可以使用.bind
:
var tag = document.createElement.bind(document); var btn = tag('button');
出现此错误的原因是该方法丢失了其上下文。 必须在document
对象的上下文中调用createElement()
方法。
在控制台中尝试这个:
var tag = document.createElement; tag.call(document, "div"); // no error tag("div"); // error
必须在document
上下文中调用createElement()
的具体细节是特定于实现的,但很容易被猜到。
因此,要维护上下文,请为document.createElement()
创建一个函数包装器:
function tag(tagName) { return document.createElement(tagName); }
当然,jQuery也会为你创建元素:
$(""); // new div element