2012-09-04 186 views
4

該字符串有78個字符的HTML和39個字符未經HTML:截斷文本,但不截斷HTML

<p>I really like the <a href="http://google.com">Google</a> search engine.</p> 

我想基於非HTML字符計數以截斷該字符串,因此,例如,如果我想截斷上面的字符串爲24個字符,則輸出將是:

I really like the <a href="http://google.com">Google</a> 

確定字符切斷的數量時,截斷並沒有考慮到的HTML,它僅考慮了剝離計數。但是,它沒有留下開放的HTML標籤。

+1

我建議你看看XML解析器;他們可能是唯一的方法來確保您不會破壞HTML /知道什麼是或不是顯示的文本。 – KRyan

回答

8

好吧,所以這是我放在一起,它似乎是工作:

function truncate_html($string, $length, $postfix = '&hellip;', $isHtml = true) { 
    $string = trim($string); 
    $postfix = (strlen(strip_tags($string)) > $length) ? $postfix : ''; 
    $i = 0; 
    $tags = []; // change to array() if php version < 5.4 

    if($isHtml) { 
     preg_match_all('/<[^>]+>([^<]*)/', $string, $tagMatches, PREG_OFFSET_CAPTURE | PREG_SET_ORDER); 
     foreach($tagMatches as $tagMatch) { 
      if ($tagMatch[0][1] - $i >= $length) { 
       break; 
      } 

      $tag = substr(strtok($tagMatch[0][0], " \t\n\r\0\x0B>"), 1); 
      if ($tag[0] != '/') { 
       $tags[] = $tag; 
      } 
      elseif (end($tags) == substr($tag, 1)) { 
       array_pop($tags); 
      } 

      $i += $tagMatch[1][1] - $tagMatch[0][1]; 
     } 
    } 

    return substr($string, 0, $length = min(strlen($string), $length + $i)) . (count($tags = array_reverse($tags)) ? '</' . implode('></', $tags) . '>' : '') . $postfix; 
} 

用法:

truncate_html('<p>I really like the <a href="http://google.com">Google</a> search engine.</p>', 24); 

功能是從抓住(做了一個小的修改):

http://www.dzone.com/snippets/truncate-text-preserving-html

+1

單字母變量,沒有解釋參數是什麼。想在這裏看到一些解釋,因爲這個功能看起來相當不錯和簡潔。 – Greg

+0

這會在最後一個結束標記後添加「後綴」。這在某些情況下可能是可取的,但在我的情況下,它會導致「......」在最後一行結束。不是很美觀。 – Ariane