ホームページ  >  記事  >  ウェブフロントエンド  >  JavaScript でノードをラップして効率を向上_JavaScript スキルを向上させる

JavaScript でノードをラップして効率を向上_JavaScript スキルを向上させる

WBOY
WBOYオリジナル
2016-05-16 18:34:041068ブラウズ

基本的には、文字列が渡されると、それが要素ノードになります。ただし、この要素ノードは多くの層を持つこともでき、ラップされる要素は最も内側の層に配置されます。文字列を要素ノードに変換するには、いくつかの方法があります。
1、createElement、IE は要素属性をまとめて作成できますが、作成できるレイヤーは 1 つだけです。
2、innerHTML ですが、IE と FF には多くの予期せぬデフォルト動作があり、多少の追加が必要になる場合があります。
3、createContextualFragment、Operaの動作が少し変なので、要素の位置を選択して変更する必要があります。日本人によるテストの結果、文字列をノードに変換する場合、innerHTML よりもはるかに効率的かつ安全であることがわかりました。要素ノードが渡された場合はクローンを作成する必要があります。そうしないと、wrapAll になります。関数の場合は、現在の要素を渡し、そのプロパティの一部を使用してラッピング要素を作成します。
最初の実験 (ここでのwrapOuterはjQueryのwrapに相当します):

コードをコピー コードは次のとおりです:

var parseHTML = function(str) {
if(document.createRange){
var range = document.createRange()
range.setStartAfter(document.body)
return range.createContextualFragment(str)
}else{
return document.createElement(str)
}
}
var WrapOuter = function(target,html){
var Wrap = parseHTML (html) ;
target.parentNode.insertBefore(wrap,target);
target.previousSibling.appendChild(target)



[Ctrl A すべて選択 注: 外部 Js を導入する必要がある場合は、更新して実行する必要があります ]

Opera にいくつかの 問題 があることが判明しました。range.setStartAfter(document.body) をターゲット要素に変更する必要があります。さらに、ラップされた要素の挿入方法が insertBefore から replaceChild に変更され、効率が向上しました。

コードをコピー コードは次のとおりです。

var WrapOuter = function(target,html) {
var Wrap = html
if(Object.prototype.toString.call(html) === "[オブジェクト文字列]"){
if(document.createRange){
var range= document.createRange ();
range.selectNodeContents(target);
wrap = range.createContextualFragment(html).firstChild;
wrap = document.createElement(str); >}
}
target.parentNode.replaceChild(wrap,target);
wrap.appendChild(target)
}




[Ctrl A すべて選択 注: 外部 Js を導入する必要がある場合は、更新して実行する必要があります ]

コードをコピーします コードは次のとおりです:

//一致する各要素に親要素 (ラップされた要素) を追加します。
wrap:function(html){//html は要素ノードまたは HTML フラグメントにすることができます
var _wrap = function (target,html){
var ラップ;
if(is(html,"String")){
if(document.createRange){
var range=document.createRange( ); 🎜>range.selectNodeContents(target);
wrap = range.createContextualFragment(html).firstChild;
}else {
wrap = document.createElement(html)
}else if(html.nodeType){
wrap = html.cloneNode(true)
}
target.parentNode.replaceChild(wrap,target);
wrap.appendChild(target)
}
if(is(html,"Function")){
return this.each(function(el,index){
_wrap(el, html.call(el,index));
} );
}
return this.each(function(el){
_wrap(el,html)
});


ラップされた要素を作成するメソッド:


コードをコピー コードは次のとおりです: var _parseHTML = function(el,html){
var Wrap = html;
if(doc.createRange){
var range=doc.createRange();
var Wrap = range.createContextualFragment(html).firstChild;
range.detach();
return dom.parseHTML(html); >}
//一致する各要素に親要素 (ラップされた要素) を追加します。
wrap:function(html){//html は要素ノードまたは HTML フラグメントにすることができます
var _wrap = function( target,html){
var Wrap = html;
if(!wrap.nodeType){
wrap = dom._parseHTML(target,html);
wrap = html .cloneNode(true)
}
target.parentNode.replaceChild(wrap,target);
wrap.insertBefore(target,null)
}
if(is(html ,"関数" )){
return this.each(function(el,index){
_wrap(el, html.call(el,index));
});
}
return this .each(function(el){
_wrap(el,html)
});
},
wrapInner:function(html){
var _wrap = function( target,html) {
var Wrap = html;
if(!wrap.nodeType){
wrap = dom._parseHTML(target,html);
wrap = html .cloneNode(true) )
}
target.insertBefore(wrap,target.firstChild);
for(var i=1,n=target.childNodes.length;iwrap.appendChild (target.childNodes[i],null)
}
}
if(is(html,"Function")){
return this.each(function(el,index ){
_wrap(el, html.call(el,index));
})
}
return this.each(function(el){
_wrap(el,html )
});
},
//一致するすべての要素をタグでラップします
//メソッド: 最初に一致した要素に親要素 (ラップ) を追加し、次に一致する他の要素をラップします 要素が転送されますこの親要素に
//wrapAll(html) WrapAll(elem)
wrapAll:function(html){
var Wrap = html;
if(!wrap.nodeType)
wrap = dom._parseHTML(this[0],html);
this[0].parentNode.replaceChild(wrap,this[0]);
return this.each(function(el){
wrap. insertBefore(el,null);
},




jQuery 公式 Web サイト

を見てみましょう。ノードをラップする方法がアップグレードされ、一度に多くのレイヤーをラップできることがわかりましたが、私の場合は一度に 1 つのレイヤーしかラップできません。そこで、オリジナルの parseHTML メソッドを呼び出すことにしました。

こちら

を参照してください。

コードをコピー コードは次のとおりです:

var Wrap = function(html){//html は要素ノードまたは HTML フラグメントにすることができます。
var _wrap = function(target,html){
var Wrap = html; if(!wrap.nodeType){
if(doc.createRange){
var range=doc.createRange();
range.selectNodeContents(target);
wrap = range.createContextualFragment( html) ).firstChild;
}else{
wrap = dom.parseHTML(html,null,true).firstChild
}
}else{
wrap = html.cloneNode(true)
}
target.parentNode.replaceChild(wrap,target);
while (wrap.firstChild && Wrap.firstChild.nodeType === 1 ) {
wrap = Wrap.firstChild>}
wrap.insertBefore(target,null)
}
if(is(html,"Function")){
return this.each(function(el,index){
_wrap( el , html.call(el,index));
})
}
return this.each(function(el){
_wrap(el,html)
}); 🎜>}
//一致する各要素の子ノードを何かでラップします。
var WrapInner = function(html){
var _wrap = function(target,html){
var Wrap = html ;
if(!wrap.nodeType){
wrap = dom.parseHTML(html,null,true).firstChild
}else{
wrap = html.cloneNode(true)
}
target.insertBefore(wrap,target.firstChild);
while (wrap.firstChild && Wrap.firstChild.nodeType === 1 ) {
wrap = Wrap.firstChild>}
(var i=1,n=target.childNodes.length;iwrap.appendChild(target.childNodes[i],null)
}
}
if( is(html,"関数")){
return this.each(function(el,index){
_wrap(el, html.call(el,index));
} ); >}
return this.each(function(el){
_wrap(el,html)
});
}
// 一致する要素をすべてタグ
でラップします/メソッド: 最初に一致した要素に親要素 (ラッパー) を追加し、その後、他の一致する要素をこの親要素に転送します
//wrapAll(html) WrapAll(elem)
var WrapAll = function(html){
var Wrap = html;
if(!wrap.nodeType){
if(doc.createRange){
var range = doc.createRange(); 0]);
wrap = range.createContextualFragment(html).firstChild;
}else{
wrap = dom.parseHTML(html,null,true).firstChild
}
} {
wrap = html.cloneNode(true)
}
this[0].parentNode.replaceChild(wrap,this[0])
while (wrap.firstChild &&wrap.firstChild.nodeType === 1 ) {
wrap = Wrap.firstChild;
}
return this.each(function(el){
wrap.insertBefore(el, null);
});
}


重複したコードがたくさんあることがわかり、もう少し抽象化すると、外部の人にはまったく理解できなくなります。jQuery もこれを段階的に実行しているのだと思います。不明瞭なものへ。



コードをコピー

if(document.createRange){
var range= dom.doc.createRange();
range.selectNodeContents(target);
wrap = range.createContextualFragment(html).firstChild;
wrap = dom.parseHTML( html,null ,true).firstChild
}
}else{
wrap = html.cloneNode(true)
}
var insertor = Wrap
while ( insertor.firstChild && insertor.firstChild .nodeType === 1 ) {
insertor = insertor.firstChild;
}
return [wrap,insertor]
}
// 一致する要素をすべてタグ / /メソッド: 最初に一致した要素に親要素 (ラッパー) を追加し、その後、他の一致する要素をこの親要素に転送します
//wrapAll(html) WrapAll(elem)
var WrapAll = function( html){
if ( dom.isFunction( html ) ) {
return this.each(function(el,index) {
dom(this).wrapAll( html.call(this,index)) ;
});
}
var arr = WrapHelper(this[0],html);
var Wrap = arr[0],insertor =arr[1]; 0].parentNode.replaceChild(wrap,this[0]);
return this.each(function(el){
insertor.insertBefore(el,null);
});
//親要素 (ラップされた要素) を一致する各要素に追加します。
var Wrap= function( html ) {
return this.each(function() {
dom( this ).wrapAll ( html );
});
}
// 一致する各要素の子ノードを何かでラップします
var WrapInner = function(html){
var _wrap = function(target, html){
var arr = WrapHelper(target,html);
var Wrap = arr[0],insertor =arr[1];
target.insertBefore(wrap, target.firstChild); >for(var i=1,n=target.childNodes.length;iinsertor.appendChild(target.childNodes[i],null)
}
}
if(is(html,"Function")){
return this.each(function(el,index){
_wrap(el, html.call(el,index)) ;
});
}
return this.each(function(el){
_wrap(el,html)
});
}
return {
wrapAll:wrapAll,
wrap:wrap,
wrapInner:wrapInner
}
})());


unwrap メソッドについては後で説明します。
声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。