Вызов всех гуру PHP!
Я понимаю, что вы можете использовать getimagesize (), чтобы получить фактическую высоту и ширину изображения в пикселях в PHP. Однако, если вы откроете изображение в Photoshop и посмотрите диалоговое окно размера изображения, вы заметите, что существует значение разрешения, которое определяет размер печати изображения.
Учитывая произвольный файл изображения jpg, мне нужно использовать PHP для определения этого числа разрешения. Похоже, что эта информация где-то хранится в файле jpg, как мне к ней добраться?
Еще одно требование - мне доступен только gdlib. Мне нужно сделать это без использования других библиотек php (imagemagick и т. д.)
Спасибо за помощь!






Вы можете просто прочитать файл JPEG напрямую, байты 14-18 указывают:
См. Также: http://www.obrador.com/essentialjpeg/headerinfo.htm
@Rafe - Конечно, с использованием функции файловой системы. Картинки тоже люди.
В зависимости от того, как изображение сохранено, EXIF содержит метрическую массу информации - подробнее об этом читайте в Руководство по PHP. Однако вам может потребоваться немного проанализировать / обработать результаты (например, информация о флэш-памяти представляет собой или, по крайней мере, была просто байтом, выражающим различные состояния).
Я не думаю, что EXIF содержит информацию о разрешении / плотности. Кроме того, php EXIF требует, чтобы php был скомпилирован с exif lib, что противоречит требованиям, указанным в моем вопросе.
РЕШЕНИЕ: воспользуйтесь набором инструментов метаданных PHP JPEG, загружаемым отсюда: http://www.ozhiker.com/electronics/pjmt/
В этом наборе инструментов есть несколько удобных сценариев, которые будут делать все, что угодно, включая просмотр и редактирование заголовка, метаданных и информации jfif в файле jpeg. Вот сценарий, который дает вам XDensity и YDensity (разрешение печати x и y) jpg:
<?php
include_once("./JPEG.php");
include_once("./JFIF.php");
$image_header = get_jpeg_header_data("./myImage.jpg");
$image_info = get_JFIF($image_header);
print( "XDensity:" . $image_info['XDensity'] . "<br />");
print( "YDensity:" . $image_info['YDensity'] . "<br />");
?>
Вау, отличный сценарий. Он действительно предоставляет массу информации об изображении. Спасибо @Rafe!
Я этого не понимаю. Пиксели = размер печати x разрешение, а количество пикселей - заданное значение. Итак, если у вас есть изображение размером 300x300 пикселей, у вас есть 1 x1 с разрешением 300 DPI, 2 x2 с разрешением 150 DPI или 4 x4 с разрешением 75 DPI и т. д. Изображение не имеет разрешения, если оно не имеет физического размер для сравнения с размером пикселя.
Что мне не хватает? (и насколько это очевидно для всех? =])
Именно Джо. XDensity и YDensity - это значения, которые я искал. Вместе с высотой и шириной в пикселях они определяют разрешение печати изображения.
Кроме того, чтобы уточнить, изображения JPEG имеют дополнительный раздел метаданных JFIF, который может включать в себя плотность x и y. Если эта информация отсутствует, графические приложения обычно по умолчанию используют разрешение 72 dpi, но у вас всегда есть возможность изменить это значение, по крайней мере, в Photoshop.
Я думаю, вы упускаете точку зрения Джей Би. У вас есть X пикселей, высеченных в камне. Если у вас есть определенный размер печати, который также высечен в камне, вы можете определить свое разрешение и не можете его увеличивать. Если у вас есть высочайшее разрешение, вы можете определить размер отпечатка и не можете его увеличить.
Есть два места, где потенциально может быть сохранено разрешение (то есть разрешение JPEG при печати, также сокращенно DPI или точек на дюйм).
Первый находится в заголовке JFIF JPEG, который часто (но НЕ всегда) находится прямо в начале JPEG.
Другой находится в данных EXIF.
Обратите внимание, что данные разрешения обычно НЕ присутствуют, поскольку они имеют значение только в том случае, если они связаны с физическим размером вывода. Например. если цифровая камера записывает значение, это обычно бессмысленно. Однако, когда JPEG выводится на принтер (например), значение будет иметь значение.
Вот код для его получения из заголовка JFIF, если он присутствует и находится внутри блока APP0, который является вторым блоком в файле. (Первым фрагментом всегда является маркер SOI.):
function read_JFIF_dpi($filename)
{
$dpi = 0;
$fp = @fopen($filename, r);
if ($fp) {
if (fseek($fp, 6) == 0) { // JFIF often (but not always) starts at offset 6.
if (($bytes = fread($fp, 16)) !== false) { // JFIF header is 16 bytes.
if (substr($bytes, 0, 4) == "JFIF") { // Make sure it is JFIF header.
$JFIF_density_unit = ord($bytes[7]);
$JFIF_X_density = ord($bytes[8])*256 + ord($bytes[9]); // Read big-endian unsigned short int.
$JFIF_Y_density = ord($bytes[10])*256 + ord($bytes[11]); // Read big-endian unsigned short int.
if ($JFIF_X_density == $JFIF_Y_density) { // Assuming we're only interested in JPEGs with square pixels.
if ($JFIF_density_unit == 1) $dpi = $JFIF_X_density; // Inches.
else if ($JFIF_density_unit == 2) $dpi = $JFIF_X_density * 2.54; // Centimeters.
}
}
}
}
fclose($fp);
}
return ($dpi);
}
Это фантастическая информация. Как теперь прочитать эту информацию с помощью PHP?