How can I truncate a string after 20 words in PHP?
function limit_text($text, $limit) {
if (str_word_count($text, 0) > $limit) {
$words = str_word_count($text, 2);
$pos = array_keys($words);
$text = substr($text, 0, $pos[$limit]) . '...';
}
return $text;
}
echo limit_text('Hello here is a long sentence that will be truncated by the', 5);
Outputs:
Hello here is a long ...
Change the number 3 to the number 20 below to get the first 20 words, or pass it as parameter. The following demonstrates how to get the first 3 words: (so change the 3 to 20 to change the default value):
function first3words($s, $limit=3) {
return preg_replace('/((\w+\W*){'.($limit-1).'}(\w+))(.*)/', '${1}', $s);
}
var_dump(first3words("hello yes, world wah ha ha")); # => "hello yes, world"
var_dump(first3words("hello yes,world wah ha ha")); # => "hello yes,world"
var_dump(first3words("hello yes world wah ha ha")); # => "hello yes world"
var_dump(first3words("hello yes world")); # => "hello yes world"
var_dump(first3words("hello yes world.")); # => "hello yes world"
var_dump(first3words("hello yes")); # => "hello yes"
var_dump(first3words("hello")); # => "hello"
var_dump(first3words("a")); # => "a"
var_dump(first3words("")); # => ""
To Nearest Space
Truncates to nearest preceding space of target character. Demo
$str The string to be truncated
$chars The amount of characters to be stripped, can be overridden by $to_space
$to_space boolean for whether or not to truncate from space near $chars limit
Function
function truncateString($str, $chars, $to_space, $replacement="...") {
if($chars > strlen($str)) return $str;
$str = substr($str, 0, $chars);
$space_pos = strrpos($str, " ");
if($to_space && $space_pos >= 0)
$str = substr($str, 0, strrpos($str, " "));
return($str . $replacement);
}
Sample
<?php
$str = "this is a string that is just some text for you to test with";
print(truncateString($str, 20, false) . "\n");
print(truncateString($str, 22, false) . "\n");
print(truncateString($str, 24, true) . "\n");
print(truncateString($str, 26, true, " :)") . "\n");
print(truncateString($str, 28, true, "--") . "\n");
?>
Output
this is a string tha...
this is a string that ...
this is a string that...
this is a string that is :)
this is a string that is--
use explode() .
Example from the docs.
// Example 1
$pizza = "piece1 piece2 piece3 piece4 piece5 piece6";
$pieces = explode(" ", $pizza);
echo $pieces[0]; // piece1
echo $pieces[1]; // piece2
note that explode has a limit function. So you could do something like
$message = implode(" ", explode(" ", $long_message, 20));
Try regex.
You need something that would match 20 words (or 20 word boundaries).
So (my regex is terrible so correct me if this isn't accurate):
/(\w+\b){20}/
And here are some examples of regex in php.
Simple and fully equiped truncate() method:
function truncate($string, $width, $etc = ' ..')
{
$wrapped = explode('$trun$', wordwrap($string, $width, '$trun$', false), 2);
return $wrapped[0] . (isset($wrapped[1]) ? $etc : '');
}
Its not my own creation, its a modification of previous posts. credits goes to karim79.
function limit_text($text, $limit) {
$strings = $text;
if (strlen($text) > $limit) {
$words = str_word_count($text, 2);
$pos = array_keys($words);
if(sizeof($pos) >$limit)
{
$text = substr($text, 0, $pos[$limit]) . '...';
}
return $text;
}
return $text;
}
If you code on Laravel just use Illuminate\Support\Str
here is example
Str::words($category->publication->title, env('WORDS_COUNT_HOME'), '...')
Hope this was helpful.
Split the string (into an array) by <space>, and then take the first 20 elements of that array.
With triple dots:
function limitWords($text, $limit) {
$word_arr = explode(" ", $text);
if (count($word_arr) > $limit) {
$words = implode(" ", array_slice($word_arr , 0, $limit) ) . ' ...';
return $words;
}
return $text;
}
Try below code,
$text = implode(' ', array_slice(explode(' ', $text), 0, 32))
echo $text;
Something like this could probably do the trick:
<?php
$words = implode(' ', array_slice(split($input, ' ', 21), 0, 20));
use PHP tokenizer function strtok() in a loop.
$token = strtok($string, " "); // we assume that words are separated by sapce or tab
$i = 0;
$first20Words = '';
while ($token !== false && $i < 20) {
$first20Words .= $token;
$token = strtok(" ");
$i++;
}
echo $first20Words;
based on 動靜能量's answer:
function truncate_words($string,$words=20) {
return preg_replace('/((\w+\W*){'.($words-1).'}(\w+))(.*)/', '${1}', $string);
}
or
function truncate_words_with_ellipsis($string,$words=20,$ellipsis=' ...') {
$new = preg_replace('/((\w+\W*){'.($words-1).'}(\w+))(.*)/', '${1}', $string);
if($new != $string){
return $new.$ellipsis;
}else{
return $string;
}
}
This worked me for UNICODE (UTF8) sentences too:
function myUTF8truncate($string, $width){
if (mb_str_word_count($string) > $width) {
$string= preg_replace('/((\w+\W*|| [\p{L}]+\W*){'.($width-1).'}(\w+))(.*)/', '${1}', $string);
}
return $string;
}
Here is what I have implemented.
function summaryMode($text, $limit, $link) {
if (str_word_count($text, 0) > $limit) {
$numwords = str_word_count($text, 2);
$pos = array_keys($numwords);
$text = substr($text, 0, $pos[$limit]).'... Read More';
}
return $text;
}
As you can see it is based off karim79's answer, all that needed changing was that the if statement also needed to check against words not characters.
I also added a link to main function for convenience. So far it hsa worked flawlessly. Thanks to the original solution provider.
Here's one I use:
$truncate = function( $str, $length ) {
if( strlen( $str ) > $length && false !== strpos( $str, ' ' ) ) {
$str = preg_split( '/ [^ ]*$/', substr( $str, 0, $length ));
return htmlspecialchars($str[0]) . '…';
} else {
return htmlspecialchars($str);
}
};
return $truncate( $myStr, 50 );
Another solution :)
$aContent = explode(' ', $cContent);
$cContent = '';
$nCount = count($aContent);
for($nI = 0; ($nI < 20 && $nI < $nCount); $nI++) {
$cContent .= $aContent[$nI] . ' ';
}
trim($cContent, ' ');
echo '<p>' . $cContent . '</p>';
To limit words, am using the following little code :
$string = "hello world ! I love chocolate.";
$explode = array_slice(explode(' ', $string), 0, 4);
$implode = implode(" ",$explode);
echo $implode;
$implot will give : hello world ! I
function getShortString($string,$wordCount,$etc = true)
{
$expString = explode(' ',$string);
$wordsInString = count($expString);
if($wordsInString >= $wordCount )
{
$shortText = '';
for($i=0; $i < $wordCount-1; $i++)
{
$shortText .= $expString[$i].' ';
}
return $etc ? $shortText.='...' : $shortText;
}
else return $string;
}
Simpler than all previously posted regex techniques, just match the first n sequences of non-word followed by sequences of word characters. Making the non-word characters optional allows matching of word characters from the start of the string. Greedy word character matching ensures that consecutive word characters are never treated as individual words.
By writing \K in the pattern after matching n substrings, then matching the rest of the string (add the s pattern modifier if you need dots to match newlines), the replacement can be an empty string.
Code: (Demo)
function firstNWords(string $string, int $limit = 3) {
return preg_replace("/(?:\W*\w+){{$limit}}\K.*/", '', $string);
}
Lets assume we have the string variables $string, $start, and $limit we can borrow 3 or 4 functions from PHP to achieve this. They are:
script_tags() PHP function to remove the unnecessary HTML and PHP
tags (if there are any). This wont be necessary, if there are no HTML or PHP tags.
explode() to split the $string into an array
array_splice() to specify the number of words and where it'll start
from. It'll be controlled by vallues assigned to our $start and $limit variables.
and finally, implode() to join the array elements into your truncated
string..
function truncateString($string, $start, $limit){
$stripped_string =strip_tags($string); // if there are HTML or PHP tags
$string_array =explode(' ',$stripped_string);
$truncated_array = array_splice($string_array,$start,$limit);
$truncated_string=implode(' ',$truncated_array);
return $truncated_string;
}
It's that simple..
I hope this was helpful.
I made my function:
function summery($text, $limit) {
$words=preg_split('/\s+/', $text);
$count=count(preg_split('/\s+/', $text));
if ($count > $limit) {
$text=NULL;
for($i=0;$i<$limit;$i++)
$text.=$words[$i].' ';
$text.='...';
}
return $text;
}
function limitText($string,$limit){
if(strlen($string) > $limit){
$string = substr($string, 0,$limit) . "...";
}
return $string;
}
this will return 20 words. I hope it will help
$text='some text';
$len=strlen($text);
$limit=500;
// char
if($len>$limit){
$text=substr($text,0,$limit);
$words=explode(" ", $text);
$wcount=count($words);
$ll=strlen($words[$wcount]);
$text=substr($text,0,($limit-$ll+1)).'...';
}
function wordLimit($str, $limit) {
$arr = explode(' ', $str);
if(count($arr) <= $limit){
return $str;
}
$result = '';
for($i = 0; $i < $limit; $i++){
$result .= $arr[$i].' ';
}
return trim($result);
}
echo wordLimit('Hello Word', 1); // Hello
echo wordLimit('Hello Word', 2); // Hello Word
echo wordLimit('Hello Word', 3); // Hello Word
echo wordLimit('Hello Word', 0); // ''
I would go with explode() , array_pop() and implode(), eg.:
$long_message = "I like summer, also I like winter and cats, btw dogs too!";
$trimmed_message = explode(" ", $long_message, 5); // <-- '5' means 4 words to be returned
array_pop($trimmed_message); //removing last element from exploded array
$trimmed_message = implode(" ", $trimmed_message) . '...';
Result:
I like summer, also...
what about
chunk_split($str,20);
Entry in the PHP Manual
function limit_word($start,$limit,$text){
$limit=$limit-1;
$stripped_string =strip_tags($text);
$string_array =explode(' ',$stripped_string);
if(count($string_array)>$limit){
$truncated_array = array_splice($string_array,$start,$limit);
$text=implode(' ',$truncated_array).'...';
return($text);
}
else{return($text);}
}
I have a comment system in my website and some users write very long comments, longer than 500 chars and I need to cut it after 200 and add the option "see more". The problem is that users can use <a>test</a> tags and in some cases the limit of 200 chars cuts the tag in the middle , like <a>t or <a or <a>test</ If any of the cases above happens, the limit should extend until the end of the html tag so ex <a>test</a>
I have this code:
function truncate($string,$length=200,$append="…") {
$string = trim($string);
if(strlen($string) > $length) {
$string = wordwrap($string, $length);
$string = explode("\n", $string, 2);
$string = $string[0] . $append;
}
return $string;
}
Any idea how to make this?
Thanks
Well, I think I did it. If anyone has any suggestion, feel free to modify this answer or comment.
function cut_text($string, $length = 350, $append = "…")
{
$string = trim($string);
$string_length = strlen($string);
$original_string = $string;
if ($string_length > $length) {
$remaining_chars = $string_length - $length;
if (strpos($string, '<') !== false && strpos($string, '>') !== false) {
$string = wordwrap($string, $length);
$string = explode("\n", $string, 2);
$string = $string[0] . $append;
$fillimi = substr_count($string, '<');
$fundi = substr_count($string, '>');
if ($fillimi == $fundi) {
$string = $string;
} else {
$i = 1;
while ($i <= $remaining_chars) {
$string = wordwrap($original_string, $length + $i);
$string = explode("\n", $string, 2);
$new_remaining_chars = $string_length - ($length + $i);
if ($new_remaining_chars > 0) {
$string = $string[0] . $append;
} else {
$string = $string[0];
}
$fillimi = substr_count($string, '<');
$fundi = substr_count($string, '>');
if ($fillimi == $fundi) {
$string = $string;
break;
}
$i++;
}
}
} else {
$string = trim($string);
$string = wordwrap($string, $length);
$string = explode("\n", $string, 2);
$string = $string[0] . $append;
}
}
return $string;
}
I think there should be this already somewhere on Internet but wasn't able to find it. What you basically need to do is count the opened tags and then if there are more opened tags than closed, it is open and can't cut yet. Here is something to push you on right direction for how to easily count the number of tags opened and closed.
I want to make a sub-string, where the $count only counts letters, not spaces. This is what I have so far:
$string ="vikas tyagi php";
$string = substr($string, 0, 10);
echo $string;
Output:
vikas tyag
Desired output (I don't want to count the spaces):
vikas tyagi
How would I do this?
i want extract string with those condition
1)Base on count letter
2)Without white space
3)String limit also
Simply count the spaces and add them to the desired length of the capture:
function spaceless_substr($string, $start, $count) {
return substr($string, $start, ($count+substr_count($string, ' ', $start, $count)));
}
$string ="vikas tyagi asd sd as asd";
echo substr($string, 0, 14);
// return: "vikas tyagi a"
echo spaceless_substr($string, 0, 14);
// return: "vikas tyagi asd"
If I understand you correctly you can do it like so:
<?php
$string = "vikas tyagi";
$lettercount = strlen(str_replace(' ', '', $string));
echo $string . ' contains ' . $lettercount . ' letters';
?>
Here I've used strlen() on a version of $string with spaces removed using str_replace()
Addition
I didn't understand the question
Addition
Here's my first crack at this, feel free to amend where you see fit:
$string = "vikas tyagi";
function my_substr($string, $start, $length)
{
$substr = substr($string, $start, $length);
$spaces = count(explode(' ', $substr)) - 1;
if ($spaces > 0)
{
return substr($string, $start, $length + $spaces);
}
return $substr;
}
echo my_substr($string, 0, 10);
$arr = explode(" ",$str);
$length = 10;
for ($i = 0, $currIndex = 0, $finalstring = ""; $currIndex < $length; $i++){
$finalstring .= " ".substr($arr[$i], 0, $length - $currIndex);
$currIndex += strlen($arr[$i]);
}
Here is a demonstration: http://codepad.org/lv4KEsAi
I need a good fast function that shortens strings to a set length with UTF8 support. Adding trailing '...' at ends is a plus. Can anyone help?
Assuming mb_* functions installed.
function truncate($str, $length, $append = '…') {
$strLength = mb_strlen($str);
if ($strLength <= $length) {
return $str;
}
return mb_substr($str, 0, $length) . $append;
}
CodePad.
Keep in mind this will add one character (the elipsis). If you want the $append included in the length that is truncated, just minus the mb_strlen($append) from the length of the string you chop.
Obviously, this will also chop in the middle of words.
Update
Here is a version that can optionally preserve whole words...
function truncate($str, $length, $breakWords = TRUE, $append = '…') {
$strLength = mb_strlen($str);
if ($strLength <= $length) {
return $str;
}
if ( ! $breakWords) {
while ($length < $strLength AND preg_match('/^\pL$/', mb_substr($str, $length, 1))) {
$length++;
}
}
return mb_substr($str, 0, $length) . $append;
}
CodePad.
It will preserve all letter characters up to the first non letter character if the third argument is TRUE.
I guess you need to truncate text, so this may be helpful:
if (!function_exists('truncate_string')) {
function truncate_string($string, $max_length) {
if (mb_strlen($string, 'UTF-8') > $max_length){
$string = mb_substr($string, 0, $max_length, 'UTF-8');
$pos = mb_strrpos($string, ' ', false, 'UTF-8');
if($pos === false) {
return mb_substr($string, 0, $max_length, 'UTF-8').'…';
}
return mb_substr($string, 0, $pos, 'UTF-8').'…';
}else{
return $string;
}
}
}
This is something like #alex just posted, but it does not break words.
Try this:
$length = 100;
if(mb_strlen($text, "utf-8") > $length){
$last_space = mb_strrpos(mb_substr($text, 0, $length, "utf-8"), " ", "utf-8");
$text = mb_substr($text, 0, $last_space, "utf-8")." ...";}
Cheers...