複数の <br/> タグを含む HTML を Javascript の適切な <p> タグに変換する簡単な方法はありますか?
-
16-09-2019 - |
質問
以下のような HTML が大量にあるとします。
bla bla bla long paragraph here
<br/>
<br/>
bla bla bla more paragraph text
<br/>
<br/>
Javascriptを使用して適切なセマンティックに変換する簡単な方法はありますか <p>
タグ?例えば。:
<p>
bla bla bla long paragraph here
</p>
<p>
bla bla bla more paragraph text
</p>
出力間隔は重要ではありません。理想的には、任意の入力間隔で機能します。
正規表現を作成してみようかと考えていますが、その前に、a) 傷つく世界を避けていること、b) 他に何もないことを確認したかったのです。 Googleで検索しましたが、まだ何も見つかりません。
アドバイスをありがとうございます!
解決
私は飽きてしまいました。私は、必要に応じて最適化/微調整があると確信しています。その魔法を行うにはjQueryの少しを使用しています。 FF3で働いていました。そして、あなたの質問への答えは非常に「シンプル」な方法がイマイチということである。)
$(function() {
$.fn.pmaker = function() {
var brs = 0;
var nodes = [];
function makeP()
{
// only bother doing this if we have nodes to stick into a P
if (nodes.length) {
var p = $("<p/>");
p.insertBefore(nodes[0]); // insert a new P before the content
p.append(nodes); // add the children
nodes = [];
}
brs=0;
}
this.contents().each(function() {
if (this.nodeType == 3) // text node
{
// if the text has non whitespace - reset the BR counter
if (/\S+/.test(this.data)) {
nodes.push(this);
brs = 0;
}
} else if (this.nodeType == 1) {
if (/br/i.test(this.tagName)) {
if (++brs == 2) {
$(this).remove(); // remove this BR from the dom
$(nodes.pop()).remove(); // delete the previous BR from the array and the DOM
makeP();
} else {
nodes.push(this);
}
} else if (/^(?:p)$/i.test(this.tagName)) {
// these tags for the P break but dont scan within
makeP();
} else if (/^(?:div)$/i.test(this.tagName)) {
// force a P break and scan within
makeP();
$(this).pmaker();
} else {
brs = 0; // some other tag - reset brs.
nodes.push(this); // add the node
// specific nodes to not peek inside of - inline tags
if (!(/^(?:b|i|strong|em|span|u)$/i.test(this.tagName))) {
$(this).pmaker(); // peek inside for P needs
}
}
}
});
while ((brs--)>0) { // remove any extra BR's at the end
$(nodes.pop()).remove();
}
makeP();
return this;
};
// run it against something:
$(function(){
$("#worker").pmaker();
});
そして、これは私がに対してテストのhtml部分だっます:
<div id="worker">
bla bla bla long <b>paragraph</b> here
<br/>
<br/>
bla bla bla more paragraph text
<br/>
<br/>
this text should end up in a P
<div class='test'>
and so should this
<br/>
<br/>
and this<br/>without breaking at the single BR
</div>
and then we have the a "buggy" clause
<p>
fear the real P!
</p>
and a trailing br<br/>
</div>
そして結果ます:
<div id="worker"><p>
bla bla bla long <b>paragraph</b> here
</p>
<p>
bla bla bla more paragraph text
</p>
<p>
this text should end up in a P
</p><div class="test"><p>
and so should this
</p>
<p>
and this<br/>without breaking at the single BR
</p></div><p>
and then we have the a "buggy" clause
</p><p>
fear the real P!
</p><p>
and a trailing br</p>
</div>
他のヒント
囲み要素の子要素+テキストのそれぞれをスキャンします。あなたが「BR」要素に遭遇するたびに、「P」の要素を作成し、それに保留中のすべてのものを追加します。泡、繰り返し、すすぎます。
あなたは新しい「P」の要素に移転されているものを削除することを忘れないでください。
このライブラリ(prototype.jsの)は、この種のために有用であることがに私を発見しました事ます。
私はあなたが実際に他のものを許可していないと仮定していますあなたはシングルラインブレークを保存する必要があることがあります(すべてではありません <br />
要素が悪い)、の二重インスタンスのみを回転させたいとします。 <br />
段落区切りに。
その際、私は次のようにします。
- すべての改行を削除します
- 全体を 1 つの段落でまとめる
- 交換する
<br /><br />
と</p>\n<p>
- 最後に空の部分を削除します
<p></p>
生成された可能性のある要素
したがって、コードは次のようになります。
var ConvertToParagraphs = function(text) {
var lineBreaksRemoved = text.replace(/\n/g, "");
var wrappedInParagraphs = "<p>" + lineBreaksRemoved + "</p>";
var brsRemoved = wrappedInParagraphs.replace(/<br[^>]*>[\s]*<br[^>]*>/gi, "</p>\n<p>");
var emptyParagraphsRemoved = brsRemoved.replace(/<p><\/p>/g, "");
return emptyParagraphsRemoved;
}
注記: プロセスを示すために非常に冗長に説明しましたが、もちろん簡略化することもできます。
これによりサンプルが変わります。
bla bla bla long paragraph here
<br/>
<br/>
bla bla bla more paragraph text
<br/>
<br/>
の中へ:
<p>bla bla bla long paragraph here</p>
<p>bla bla bla more paragraph text</p>
しかし、それは何も削除せずにそうします <br />
実際に必要と思われる要素。
私ならそれをいくつかの段階で行います。
- 正規表現:すべての br タグを改行に変換します。
- 正規表現:すべての空白を削除します。
- 正規表現:複数の改行を単一の改行に変換します。
- 結果に対して Array.split(' ') を使用します。
これにより、(理論的には) すべての「実際の」段落を含む配列が得られるはずです。その後、それを反復処理して、各行を p タグで囲むだけです。