2012-01-24 2 views
5

Я использую Curl via Proxies для загрузки изображений со скребком, который я разработал.PHP: определение визуально искаженных изображений (правда, действительно), загруженных через Curl с помощью GD/Imagemagick

К сожалению, он получает странное изображение, которое выглядит как это и последний полностью пустым:/

3/4 corrupted dog corrupted room corrupted completely white

  • Когда я проверяю изображения с помощью ImageMagick (с использованием определить), это говорит мне, что они являются действительными изображениями.
  • Когда я снова тестирую изображения через exif_imagetype() и imagecreatefromjpeg(), обе эти функции говорят мне, что изображения действительны.

У кого-нибудь есть способ определить, имеет ли изображение большую часть серости или полностью пустое/белое, и это действительно искаженные изображения?

Я проделал большую проверку с другими вопросами здесь, но мне не повезло с другими решениями. Поэтому, пожалуйста, позаботьтесь о том, чтобы предположить, что это дубликат.

Благодаря


Узнав о imgcolorat, я сделал поиск и наткнулся на какой-то код. Я придумал это:

<?php 

$file = dirname(__FILE__) . "/images/1.jpg"; 

$img = imagecreatefromjpeg($file); 

$imagew = imagesx($img); 
$imageh = imagesy($img); 
$xy = array(); 

$last_height = $imageh - 5; 

$foo = array(); 

$x = 0; 
$y = 0; 
for ($x = 0; $x <= $imagew; $x++) 
{ 
    for ($y = $last_height;$y <= $imageh; $y++) 
    { 
     $rgb = @imagecolorat($img, $x, $y); 

     $r = ($rgb >> 16) & 0xFF; 
     $g = ($rgb >> 8) & 0xFF; 
     $b = $rgb & 0xFF; 

     if ($r != 0) 
     { 
      $foo[] = $r; 
     } 
    } 
} 

$bar = array_count_values($foo); 

$gray = (isset($bar['127']) ? $bar['127'] : 0) + (isset($bar['128']) ? $bar['128'] : 0) + (isset($bar['129']) ? $bar['129'] : 0); 
$total = count($foo); 
$other = $total - $gray; 

if ($gray > $other) 
{ 
    echo "image corrupted \n"; 
} 
else 
{ 
    echo "image not corrupted \n"; 
} 
?> 

Кто-нибудь видит какие-то потенциальные подводные камни с этим? Я подумал о том, чтобы получить последние несколько строк изображения, а затем сравнить общее количество 127,128,129 (серые) от общего количества других цветов. Если серый цвет больше, чем другие цвета, то изображение, безусловно, повреждено.

Мнения приветствуются! :)

+0

Хм. Если все эти функции говорят, что это действительный образ, они, вероятно, просто проверяют байты заголовка, но не смотрят, действительно ли весь файл * там *. Я бы ожидал, что там будет байт заголовка, который определяет ожидаемый, но я точно не знаю, существует ли такая вещь. –

ответ

1

Если изображение, которое он возвращает, является допустимым файлом, тогда я бы рекомендовал дважды выполнить очистку (то есть загрузить его дважды и проверить, совпадают ли они).

Другой вариант - проверить последние несколько пикселей изображения (т. Е. Нижний правый угол), чтобы убедиться, что они точно соответствуют этому цвету серого. Если они это сделают, то перезагрузите. (очевидно, что этот подход терпит неудачу, если вы загружаете изображение, которое на самом деле должно быть серым в этом углу, в этом точном цвете ... но если вы проверите несколько последних пикселей, это уменьшит вероятность этого до приемлемого уровня).

+0

* Этот второй подход предполагает, что ваш инструмент scrape фактически заполняет все изображение, а не только удушающую часть пройдите через и дайте вам частичный файл. – CasualT

+0

Я все для проверки последних нескольких пикселей изображения, чтобы увидеть, серый ли он. Я просто не знаю, как это сделать. Если вы придумали решение, пожалуйста, ознакомьтесь с представленными изображениями. – PaulM

+0

это должно сделать трюк: http://php.net/manual/en/function.imagecolorat.php – CasualT

4

нашел эту страницу при поиске способа проверки визуально поврежденных изображений, подобных этому. Вот способ решить эту проблему с помощью Баша (во всяком случае, команда новообращенной линия может быть легко адаптирована для PHP или Python):

convert INPUTFILEPATH -gravity SouthWest -crop 20%x1% -format %c -depth 8 histogram:info:- | sed '/^$/d' | sort -V | head -n 1 | grep fractal | wc -l 

Он обрежет немного площади в юго-западном углу картины, а затем получает гистограмма этого изображения. Если основной цвет гистограммы имеет название «фрактал» вместо цвета rgb, это означает, что эта зона повреждена, поэтому выход будет 1 и 0 в противном случае.

Надеюсь, это поможет!

+0

Кажется работать. Что означает «фрактал» на гистограмме? – Frans

+0

Fractal - это просто colorname для # 808080. Я знаю, что это старо, но мы только что столкнулись с проблемой, когда нижняя часть изображения действительно серьезна. Было бы очень хорошо, если бы можно было указать, какой цвет «по умолчанию» должен быть там, а не «фрактал», любые идеи? –

2

Я использую этот. Если большая часть пикселей в правом нижнем углу (5x5) серая, изображение будет разбито.

define('MIN_WIDTH',500); 
    define('MIN_HEIGHT',200); 

    function isGoodImage($fn){ 
     list($w,$h)=getimagesize($fn); 
     if($w<MIN_WIDTH || $h<MIN_HEIGHT) return 0; 
     $im=imagecreatefromstring(file_get_contents($fn)); 
     $grey=0; 
     for($i=0;$i<5;++$i){ 
      for($j=0;$j<5;++$j){ 
        $x=$w-5+$i; 
        $y=$h-5+$j; 
        list($r,$g,$b)=array_values(imagecolorsforindex($im,imagecolorat($im,$x,$y))); 
        if($r==$g && $g==$b && $b==128) 
         ++$grey; 
      } 
     } 
     return $grey<12; 
    } 
0

команда ImageMagick в identify будет определять гораздо более коррумпированные изображения, если вы звоните его с опцией -verbose. И есть опция -regard-warnings, которая заставит ее обрабатывать предупреждения как ошибки. Попробуйте их против плохого изображения и посмотрите, не является ли результатом ненулевой код ошибки.