function drupal_substr

Cuts off a piece of a string based on character indices and counts.

Follows the same behavior as PHP's own substr() function. Note that for cutting off a string at a known character/substring location, the usage of PHP's normal strpos/substr is safe and much faster.

Parameters

$text: The input string.

$start: The position at which to start reading.

$length: The number of characters to read.

Return value

The shortened string.

Related topics

12 calls to drupal_substr()
DBLogTestCase::doUser in modules/dblog/dblog.test
Generates and then verifies some user events.
drupal_ucfirst in includes/unicode.inc
Capitalizes the first letter of a UTF-8 string.
file_create_url in includes/file.inc
Creates a web-accessible URL for a stream to an external or local file.
ForumTestCase::editForumTaxonomy in modules/forum/forum.test
Edits the forum taxonomy.
menu_contextual_links in includes/menu.inc
Retrieves contextual links for a path based on registered local tasks.

... See full list

1 string reference to 'drupal_substr'
dblog_watchdog in modules/dblog/dblog.module
Implements hook_watchdog().

File

includes/unicode.inc, line 590

Code

function drupal_substr($text, $start, $length = NULL) {
    global $multibyte;
    $text = (string) $text;
    if ($multibyte == UNICODE_MULTIBYTE) {
        return $length === NULL ? mb_substr($text, $start) : mb_substr($text, $start, $length);
    }
    else {
        $strlen = strlen($text);
        // Find the starting byte offset.
        $bytes = 0;
        if ($start > 0) {
            // Count all the continuation bytes from the start until we have found
            // $start characters or the end of the string.
            $bytes = -1;
            $chars = -1;
            while ($bytes < $strlen - 1 && $chars < $start) {
                $bytes++;
                $c = ord($text[$bytes]);
                if ($c < 0x80 || $c >= 0xc0) {
                    $chars++;
                }
            }
        }
        elseif ($start < 0) {
            // Count all the continuation bytes from the end until we have found
            // abs($start) characters.
            $start = abs($start);
            $bytes = $strlen;
            $chars = 0;
            while ($bytes > 0 && $chars < $start) {
                $bytes--;
                $c = ord($text[$bytes]);
                if ($c < 0x80 || $c >= 0xc0) {
                    $chars++;
                }
            }
        }
        $istart = $bytes;
        // Find the ending byte offset.
        if ($length === NULL) {
            $iend = $strlen;
        }
        elseif ($length > 0) {
            // Count all the continuation bytes from the starting index until we have
            // found $length characters or reached the end of the string, then
            // backtrace one byte.
            $iend = $istart - 1;
            $chars = -1;
            $last_real = FALSE;
            while ($iend < $strlen - 1 && $chars < $length) {
                $iend++;
                $c = ord($text[$iend]);
                $last_real = FALSE;
                if ($c < 0x80 || $c >= 0xc0) {
                    $chars++;
                    $last_real = TRUE;
                }
            }
            // Backtrace one byte if the last character we found was a real character
            // and we don't need it.
            if ($last_real && $chars >= $length) {
                $iend--;
            }
        }
        elseif ($length < 0) {
            // Count all the continuation bytes from the end until we have found
            // abs($start) characters, then backtrace one byte.
            $length = abs($length);
            $iend = $strlen;
            $chars = 0;
            while ($iend > 0 && $chars < $length) {
                $iend--;
                $c = ord($text[$iend]);
                if ($c < 0x80 || $c >= 0xc0) {
                    $chars++;
                }
            }
            // Backtrace one byte if we are not at the beginning of the string.
            if ($iend > 0) {
                $iend--;
            }
        }
        else {
            // $length == 0, return an empty string.
            return '';
        }
        return substr($text, $istart, max(0, $iend - $istart + 1));
    }
}

Buggy or inaccurate documentation? Please file an issue. Need support? Need help programming? Connect with the Drupal community.