Passed
Push — master ( a93e2d...567501 )
by Philippe
03:03
created

LineAndOffset   A

Complexity

Total Complexity 3

Size/Duplication

Total Lines 27
Duplicated Lines 0 %

Importance

Changes 0
Metric Value
eloc 11
dl 0
loc 27
rs 10
c 0
b 0
f 0
wmc 3

1 Method

Rating   Name   Duplication   Size   Complexity  
A findFromFirstCharacterOffset() 0 19 3
1
<?php
2
3
declare(strict_types=1);
4
5
namespace PhpSpellcheck\Utils;
6
7
use PhpSpellcheck\Exception\InvalidArgumentException;
8
use Webmozart\Assert\Assert;
9
10
class LineAndOffset
11
{
12
    /**
13
     * When spellcheckers only gives the offset position of a word from the first character of the whole text
14
     * and not from the first character of the word's line, this function helps computing it anyway.
15
     *
16
     * @return array(int,int) Line number as the first element and offset from beginning of line as second element
17
     */
18
    public static function findFromFirstCharacterOffset(string $text, int $offsetFromFirstCharacter, string $encoding = TextEncoding::UTF8): array
19
    {
20
        // positive offset
21
        Assert::greaterThanEq($offsetFromFirstCharacter, 0, 'Offset must be positive');
22
23
        $textLength = mb_strlen($text);
24
        if ($textLength < $offsetFromFirstCharacter) {
25
            throw new InvalidArgumentException(
26
                \Safe\sprintf('Offset given "%d" is higher than the string length "%d"', $offsetFromFirstCharacter, $textLength)
27
            );
28
        }
29
30
        $textBeforeOffset = mb_substr($text, 0, $offsetFromFirstCharacter, $encoding);
31
        $line = mb_substr_count($textBeforeOffset, PHP_EOL) + 1;
32
        $offsetOfPreviousLinebreak = mb_strrpos($textBeforeOffset, PHP_EOL, 0, $encoding);
33
34
        $offset = $offsetFromFirstCharacter - ($offsetOfPreviousLinebreak !== false ? $offsetOfPreviousLinebreak + 1 : 0);
35
36
        return [$line, $offset];
37
    }
38
}
39