C'è un modo semplice per convertire HTML con più tag
nei tag corretti circostanti

​​Javascript?

StackOverflow https://stackoverflow.com/questions/1275250

Domanda

Diciamo che ho un po 'di HTML come di seguito:

bla bla bla long paragraph here
<br/>
<br/>
bla bla bla more paragraph text
<br/>
<br/>

C'è un modo semplice con Javascript per convertirlo correttamente i tag semantici <p>? Per esempio:.

<p>
  bla bla bla long paragraph here
</p>
<p>
  bla bla bla more paragraph text
</p>

spaziatura di uscita non è importante, in posizione ideale che possa funzionare con qualsiasi spaziatura di ingresso.

Sto pensando che potrei provare a cucinare un'espressione regolare, ma prima di farlo ho voluto assicurarsi che ero a) evitare un mondo di dolore e b) non c'era qualcos'altro là fuori - mi piacerebbe provato a fare una ricerca su Google, ma non sono ancora venuto in mente nulla.

Grazie per qualsiasi consiglio!

È stato utile?

Soluzione

mi sono annoiato. Sono sicuro che ci sono ottimizzazioni / ritocchi necessari. Utilizza un po 'di jQuery per fare la sua magia. Ha lavorato in FF3. E la risposta alla tua domanda è che c'è neanche un modo molto "semplice":)

$(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();
  });

E questa è stata la parte html ho testato contro:

<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>

E il risultato:

<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>

Altri suggerimenti

Eseguire la scansione ciascuno degli elementi figlio + testo dell'elemento di recinzione. Ogni volta che si verifica un elemento "br", creare un elemento "p", e aggiungere tutti roba in attesa di esso. Schiuma, sciacquare, ripetere.

Non dimenticare di rimuovere il materiale che si trasferiscono in un nuovo elemento "p".

Ho trovato questa libreria (prototype.js) di essere utile per questo tipo di cosa.

Sto assumendo che non stai permettendo davvero qualsiasi altra A volte è necessario per preservare la line-breaks singoli (non tutti gli elementi <br /> sono cattivi), e si desidera solo girare doppie istanze di <br /> in interruzioni di paragrafo.

In questo modo lo farei:

  1. Rimuovi tutte le interruzioni di riga
  2. Avvolgere il tutto in un paragrafo
  3. Sostituire <br /><br /> con </p>\n<p>
  4. Infine, rimuovere eventuali elementi <p></p> vuoti che potrebbero essere stati generati

Quindi, il codice potrebbe essere simile a:

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;
}

Nota. Sono stato estremamente dettagliato per mostrare i processi, che ci si è semplificare ovviamente

Questa operazione accende il campione:

bla bla bla long paragraph here
<br/>
<br/>
bla bla bla more paragraph text
<br/>
<br/>

Into:

<p>bla bla bla long paragraph here</p>
<p>bla bla bla more paragraph text</p>

Ma lo fa senza rimuovere alcun elemento <br /> che si può effettivamente desidera.

Lo farei in varie fasi:

  1. RegExp:. convertire tutti i br-tag per interruzioni di linea
  2. RegExp:. Striscia tutte le white-space
  3. RegExp: Convertire le molteplici line-breaks a quelle singole
  4. .
  5. Usa Array.split ( '\ n') sul risultato.

Questo dovrebbe dare un array con tutti i paragrafi 'reali' (in teoria). Poi si può semplicemente scorrere attraverso di essa e avvolgere ogni linea in P-tag.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top