2026-01-09 07:13:59 +00:00

56 lines
2.2 KiB
PHP

<?php declare(strict_types=1);
namespace PrinsFrank\PdfParser\Document\Dictionary\DictionaryValue\Array;
use Override;
use PrinsFrank\PdfParser\Document\Dictionary\Dictionary;
use PrinsFrank\PdfParser\Document\Dictionary\DictionaryParser;
use PrinsFrank\PdfParser\Document\Dictionary\DictionaryValue\DictionaryValue;
use PrinsFrank\PdfParser\Exception\PdfParserException;
use PrinsFrank\PdfParser\Exception\RuntimeException;
use PrinsFrank\PdfParser\Stream\InMemoryStream;
class DictionaryArrayValue implements DictionaryValue {
/** @var list<Dictionary> */
public readonly array $dictionaries;
/** @no-named-arguments */
public function __construct(
Dictionary... $dictionaries,
) {
$this->dictionaries = $dictionaries;
}
#[Override]
/** @throws PdfParserException */
public static function fromValue(string $valueString): ?self {
$valueStringWithoutSpaces = str_replace([' ', "\r", "\n"], '', $valueString);
if ((str_starts_with($valueStringWithoutSpaces, '[<<') === false && str_starts_with($valueStringWithoutSpaces, '[null') === false)
|| (str_ends_with($valueStringWithoutSpaces, '>>]') === false && str_ends_with($valueStringWithoutSpaces, 'null]') === false)) {
return null;
}
$dictionaryEntries = [];
$valueString = preg_replace('/(<<[^>]*>>)(?=<<[^>]*>>)/', '$1 $2', $valueString)
?? throw new RuntimeException('An error occurred while sanitizing dictionary array value');
foreach (explode('>> <<', substr($valueString, 3, -3)) as $dictionaryValueString) {
$dictionaryEntries[] = $dictionaryValueString === ''
? new Dictionary()
: DictionaryParser::parse($memoryStream = new InMemoryStream('<<' . $dictionaryValueString . '>>'), 0, $memoryStream->getSizeInBytes());
}
return new self(... $dictionaryEntries);
}
public function toSingleDictionary(): ?Dictionary {
$dictionaryEntries = [];
foreach ($this->dictionaries as $dictionary) {
foreach ($dictionary->dictionaryEntries as $dictionaryEntry) {
$dictionaryEntries[] = $dictionaryEntry;
}
}
return new Dictionary(... $dictionaryEntries);
}
}