(PHP 4 >= 4.2.0, PHP 5, PHP 7, PHP 8)
exif_read_data — Читает заголовки EXIF из файлов изображений
$file
,$required_sections
= null
,$as_arrays
= false
,$read_thumbnail
= false
Функция exif_read_data() читает заголовки EXIF из файлов изображений. Так читают метаданные, которые генерируют цифровые фотоаппараты.
По идее, EXIF-заголовки должны идти первыми в JPEG- или TIFF-файлах, которые генерируют фотоаппараты. Но, к сожалению, каждый производитель по-своему представляет, как компоновать метаданные изображения. Поэтому будьте готовы к ситуации, когда перед Exif-заголовком есть ещё что-то.
Значения Height
и Width
функция вычисляет аналогично вычислениям функции getimagesize(), так что эти параметры не обязаны присутствовать в заголовке. html
— текстовая строка, которая задаёт высоту и ширину, которую можно использовать в обычном HTML.
Если Exif-заголовок содержит сообщение об авторских правах, само сообщение может содержать 2 значения. Стандарт Exif 2.10 не описывает эту ситуацию, поэтому раздел COMPUTED
будет содержать оба этих значения в полях Copyright.Photographer
и Copyright.Editor
. В то же время разделы IFD0
будут содержать массив байтов с NULL-символом в качестве разделителя этих двух значений либо только первое значение, если тип файла определился неверно (нормальная ситуация для Exif). Раздел COMPUTED
будет также содержать Copyright
, который бывает либо исходной строкой, либо списком из владельца фотографии и редактора через запятую.
Тег UserComment
содержит те же проблемы, что и Copyright. Он может хранить 2 значения. Первое — кодировку, второе — само значение. В этом случае раздел IFD
содержит либо кодировку, либо массив байтов. Раздел COMPUTED
будет хранить оба этих значения в полях UserCommentEncoding
и UserComment
. Содержимое тега UserComment
будет доступно в любом случае, поэтому лучше использовать этот тег вместо раздела IFD0
.
Также exif_read_data() проверяет EXIF-теги на соответствие спецификации EXIF (» http://exif.org/Exif2-2.PDF, стр. 20).
file
Местоположение файла с изображением. Может быть как путём к файлу, так и потоковым ресурсом (можно использовать обёртки).
required_sections
Список разделённых запятой разделов, которые должны быть представлены в результирующем массиве (array). Если ни один из разделов найти не удастся, функция вернёт false
.
FILE | FileName, FileSize, FileDateTime, SectionsFound |
COMPUTED | html, Width, Height, IsColor, и другие. Height и Width вычисляются аналогично getimagesize(), поэтому их не обязательно включать в заголовок. html — текстовая строка, задающая высоту/ширину, которую можно использовать в обычном HTML. |
ANY_TAG | Любая информация заключённая в тег, например, IFD0 , EXIF , ... |
IFD0 | Все данные тега IFD0. В обычных изображениях в нем хранится размер изображения. |
THUMBNAIL | Если файл содержит второй раздел IFD , то считается, что у изображения есть эскиз. Вся информация об эскизе хранится в этом разделе. |
COMMENT | Заголовки комментариев JPEG изображений. |
EXIF | Раздел EXIF является подразделом IFD0 . Он содержит более детальную информацию об изображении. Большинство его записей зависят от фотоаппарата. |
as_arrays
Определяет, формировать ли разделы в виде массивов. Разделы required_sections
, COMPUTED
, THUMBNAIL
и COMMENT
всегда делаются массивами, так как они могут содержать значения, имена которых будут конфликтовать с именами в других разделах.
read_thumbnail
Если true
, будет прочитан сам эскиз. В противном случае будет прочитана только информация в тегах.
Возвращает ассоциативный массив (array), в котором ключами будут имена заголовков, а значениями — значения соответствующие этим заголовкам. Если никаких данных вернуть нельзя, exif_read_data() вернёт false
.
Ошибки уровня E_WARNING
и/или E_NOTICE
могут возникать для неподдерживаемых тегов или других потенциальных условий ошибки, но функция всё равно пытается прочитать всю понятную информацию.
Версия | Описание |
---|---|
8.0.0 | required_sections теперь допускает значение null. |
7.2.0 | Параметр file переименовали в stream и принимает как локальный путь к файлу, так и потоковый ресурс. |
7.2.0 | Добавили поддержку следующих форматов EXIF:
|
Пример #1 Пример использования функции exif_read_data()
<?php
echo "test1.jpg:<br />\n";
$exif = exif_read_data('tests/test1.jpg', 'IFD0');
echo $exif===false ? "Функция не нашла данные заголовка.<br />\n" : "Изображение содержит заголовки<br />\n";
$exif = exif_read_data('tests/test2.jpg', 0, true);
echo "test2.jpg:<br />\n";
foreach ($exif as $key => $section) {
foreach ($section as $name => $val) {
echo "$key.$name: $val<br />\n";
}
}
?>
Первый вызов завершается неудачей, поскольку заголовки изображения не содержат информации.
Вывод приведённого примера будет похож на:
test1.jpg: Функция не нашла данные заголовка. test2.jpg: FILE.FileName: test2.jpg FILE.FileDateTime: 1017666176 FILE.FileSize: 1240 FILE.FileType: 2 FILE.SectionsFound: ANY_TAG, IFD0, THUMBNAIL, COMMENT COMPUTED.html: width="1" height="1" COMPUTED.Height: 1 COMPUTED.Width: 1 COMPUTED.IsColor: 1 COMPUTED.ByteOrderMotorola: 1 COMPUTED.UserComment: Exif test image. COMPUTED.UserCommentEncoding: ASCII COMPUTED.Copyright: Photo (c) M.Boerger, Edited by M.Boerger. COMPUTED.Copyright.Photographer: Photo (c) M.Boerger COMPUTED.Copyright.Editor: Edited by M.Boerger. IFD0.Copyright: Photo (c) M.Boerger IFD0.UserComment: ASCII THUMBNAIL.JPEGInterchangeFormat: 134 THUMBNAIL.JPEGInterchangeFormatLength: 523 COMMENT.0: Comment #1. COMMENT.1: Comment #2. COMMENT.2: Comment #3end THUMBNAIL.JPEGInterchangeFormat: 134 THUMBNAIL.Thumbnail.Height: 1 THUMBNAIL.Thumbnail.Height: 1
Пример #2 Использование функции exif_read_data() с потоковым ресурсом (доступно с PHP 7.2.0)
<?php
// Открываем файл в бинарном режиме
$fp = fopen('/path/to/image.jpg', 'rb');
if (!$fp) {
echo 'Ошибка: Невозможно открыть файл для чтения';
exit;
}
// Попытка прочитать заголовки exif
$headers = exif_read_data($fp);
if (!$headers) {
echo 'Ошибка: невозможно прочитать заголовки exif';
exit;
}
// Напечатать заголовки 'COMPUTED'
echo 'Заголовки EXIF:' . PHP_EOL;
foreach ($headers['COMPUTED'] as $header => $value) {
printf(' %s => %s%s', $header, $value, PHP_EOL);
}
?>
Вывод приведённого примера будет похож на:
EXIF Headers: Height => 576 Width => 1024 IsColor => 1 ByteOrderMotorola => 0 ApertureFNumber => f/5.6 UserComment => UserCommentEncoding => UNDEFINED Copyright => Denis Thumbnail.FileType => 2 Thumbnail.MimeType => image/jpeg
Замечание:
Если модуль mbstring включили, то exif будет пытаться обрабатывать Юникод и брать кодировку как указано в параметрах конфигурации exif.decode_unicode_motorola и exif.decode_unicode_intel. Модуль exif не будет пытаться определить кодировку сам, правильную кодировку для декодирования указывает пользователь путём установки одной из двух INI-директив перед вызовом функции exif_read_data().
Замечание:
Если параметр
file
указали для передачи в функцию потока, поток должен быть перематываемым. Обратите внимание, что файловый позиционный указатель не изменится после завершения работы функции.