Search code examples
phpjoomlastrlenjoomla3.5

PHP mb_strlen not returning correct character count


I'm trying to get my Joomla website to display a specific amount of text from an article shown in a module. I'm using the following PHP:

<span class="rightintrotext" itemprop="introtext">

<?php 
    $length = 400; 
    if ( mb_strlen($item->introtext ) > $length ) : 
        echo ( mb_substr($item->introtext, 0, $length)) . " ... "; 
?>
<?php 
    else : 
        echo $item->introtext; 
?>
<?php 
    endif; 
?>
</span>

Which I would assume would show the first 400 characters of the article text, however it's only showing about 253 characters instead. I've got essentially no PHP experience. I was originally using strlen but read online that mb_strlen would get around my problem but nothing seems to be different between the two; the both display the wrong character count (both the same as each other).

Edit: If i include the containing <p> tag and its style (auto generated by Joomla) It is the following:

<p style="margin: 0px 0px 15px; padding: 0px; text-align: justify; color: #000000; font-family: 'Open Sans', Arial, sans-serif; font-size: 14px;">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean pharetra, leo suscipit feugiat faucibus, risus erat placerat lacus, a volutpat tellus libero a tortor. In sapien nisi, luctus sed nibh volutpat, egestas ullamcorper purus. Mauris egestas id

which is 402 characters so i assume this is where the issue lies.

I'm thinking I could just do the character count i want + the html tags count (which shouldn't change). Thoughts?


Solution

  • $item->introtext

    Is the content clean? i.e. if it contains html special chars, tags, or any other elements than varchar values?

    If not, then it is highly suggested to clean the content before applying mb_substr(). You can clean the content as::

    mb_strimwidth(strip_tags($item->introtext), 0, 400); //returns varchar substring of length 400 from first character. 
    

    You can clean the content further if you want to, like removing htmlspecialchars, htmlentities...

    UPDATE

    Replace your code with::

    <?php 
    $lenght = 400;
    echo (mb_strlen($item->introtext)>$length) ? mb_strimwidth(strip_tags($item->introtext), 0, $length, "...") : $item->introtext;
    ?>
    

    UPDATE 1

    On the edited part of your question, you stated that you want to keep the html tags + show 400 characters, it is a hard job.

    The substring you created can affect the content as ::

    • if you separate the html tags and the content, you might not know when and where the tags will appear as it is dynamic content.

    • if you keep the html tags inside the substring, you never know if the substring contains the closing tags or not which might cause a lot more harder trouble on the html structure.

    So, you have got options ::

    • neglect the html tags and show plain text (but still you can enclose it with html tags like p, span, div... and stylize) of character length 400
    • use complex mechanism of separating the html tags and showing the content. (this involves preg_match and replace, be positive: you don't want to do this)