2012-04-24 69 views
20

Tôi đang cố gắng sao chép chức năng mà Dribbble.com thực hiện với việc phát hiện các màu chủ đạo trong Hình ảnh. Trong hình dưới đây, bạn có thể thấy một ảnh chụp màn hình từ Dribbble.com cho thấy 8 màu chủ đạo trong hình ảnh ở bên trái. Đây là trang thực sự trong hình ảnh http://dribbble.com/shots/528033-Fresh-Easy?list=followingPhát hiện màu chính trong hình ảnh bằng PHP

Tôi cần phải làm điều này bằng PHP, khi tôi nhận được các màu tôi cần tôi sẽ lưu chúng vào cơ sở dữ liệu để xử lý không cần phải chạy trên mọi trang tải.

Sau một số nghiên cứu về cách lấy những màu này ra khỏi hình ảnh, một số người cho biết bạn chỉ cần kiểm tra pixel ảnh theo pixel và sau đó lưu các màu xuất hiện nhiều nhất. Nói khác có nhiều hơn với nó và rằng nhận được những màu sắc tồn tại thường xuyên nhất sẽ không cung cấp cho các ảnh hưởng mong muốn. Họ nói rằng bạn cần phải Quantize hình ảnh/màu sắc (Tôi bị mất vào thời điểm này).

Trong hình ảnh dưới đây chụp Dribble dưới đây là một thư viện Javascript rằng làm điều tương tự, trang đó có thể được xem tại đây http://lokeshdhakar.com/projects/color-thief/

Xem nguồn của trang mà tôi có thể nhìn thấy ở đó là một file javascript tên quantize.js và kết quả thực sự tốt. Vì vậy, tôi hy vọng sẽ có thể làm những gì mà thư viện Javascript không nhưng với PHP và GD/ImageMagick

enter image description here


tôi đã tìm thấy chức năng này sẽ trở lại với màu sắc và đếm trong một hình ảnh với PHP nhưng kết quả khác với phiên bản Javascript ở trên và kết quả Dribble

/** 
* Returns the colors of the image in an array, ordered in descending order, where the keys are the colors, and the values are the count of the color. 
* 
* @return array 
*/ 
function Get_Color() 
{ 
    if (isset($this->image)) 
    { 
     $PREVIEW_WIDTH = 150; //WE HAVE TO RESIZE THE IMAGE, BECAUSE WE ONLY NEED THE MOST SIGNIFICANT COLORS. 
     $PREVIEW_HEIGHT = 150; 
     $size = GetImageSize($this->image); 
     $scale=1; 
     if ($size[0]>0) 
     $scale = min($PREVIEW_WIDTH/$size[0], $PREVIEW_HEIGHT/$size[1]); 
     if ($scale < 1) 
     { 
      $width = floor($scale*$size[0]); 
      $height = floor($scale*$size[1]); 
     } 
     else 
     { 
      $width = $size[0]; 
      $height = $size[1]; 
     } 
     $image_resized = imagecreatetruecolor($width, $height); 
     if ($size[2]==1) 
     $image_orig=imagecreatefromgif($this->image); 
     if ($size[2]==2) 
     $image_orig=imagecreatefromjpeg($this->image); 
     if ($size[2]==3) 
     $image_orig=imagecreatefrompng($this->image); 
     imagecopyresampled($image_resized, $image_orig, 0, 0, 0, 0, $width, $height, $size[0], $size[1]); //WE NEED NEAREST NEIGHBOR RESIZING, BECAUSE IT DOESN'T ALTER THE COLORS 
     $im = $image_resized; 
     $imgWidth = imagesx($im); 
     $imgHeight = imagesy($im); 
     for ($y=0; $y < $imgHeight; $y++) 
     { 
      for ($x=0; $x < $imgWidth; $x++) 
      { 
       $index = imagecolorat($im,$x,$y); 
       $Colors = imagecolorsforindex($im,$index); 
       $Colors['red']=intval((($Colors['red'])+15)/32)*32; //ROUND THE COLORS, TO REDUCE THE NUMBER OF COLORS, SO THE WON'T BE ANY NEARLY DUPLICATE COLORS! 
       $Colors['green']=intval((($Colors['green'])+15)/32)*32; 
       $Colors['blue']=intval((($Colors['blue'])+15)/32)*32; 
       if ($Colors['red']>=256) 
       $Colors['red']=240; 
       if ($Colors['green']>=256) 
       $Colors['green']=240; 
       if ($Colors['blue']>=256) 
       $Colors['blue']=240; 
       $hexarray[]=substr("0".dechex($Colors['red']),-2).substr("0".dechex($Colors['green']),-2).substr("0".dechex($Colors['blue']),-2); 
      } 
     } 
     $hexarray=array_count_values($hexarray); 
     natsort($hexarray); 
     $hexarray=array_reverse($hexarray,true); 
     return $hexarray; 

    } 
    else die("You must enter a filename! (\$image parameter)"); 
} 

Vì vậy, tôi hỏi liệu có ai biết cách tôi có thể thực hiện tác vụ như vậy với PHP không? Có thể có điều gì đó đã tồn tại mà bạn biết hoặc bất kỳ mẹo nào để tôi tiến một bước gần hơn để thực hiện việc này sẽ được đánh giá cao

+0

http://stackoverflow.com/questions/3468500/detect-overall-average-color-of-the-picture –

+0

@aSeptik có vẻ như đang làm giống như mã tôi đã đăng đã là – JasonDavis

+0

bạn đã thử chưa để tìm kiếm google cho ''php lấy bảng màu từ hình ảnh" 'tôi đã thành lập rất nhiều kết quả; chỉ cần hỏi ... –

Trả lời

24

Dưới đây là chính xác những gì bạn đang tìm kiếm trong PHP: https://github.com/thephpleague/color-extractor

Ví dụ:

require 'vendor/autoload.php'; 

use League\ColorExtractor\Client as ColorExtractor; 

$client = new ColorExtractor; 

$image = $client->loadPng('./some/image.png'); 

// Get the most used color hexadecimal codes from image.png 
$palette = $image->extract(); 
+0

Điều đó giống như một nhân viên tốt cho một cổng đến C :) – quickshiftin

3

Trang bạn đã liên kết có liên kết tới mã nguồn trên GitHub vì vậy nếu bạn muốn biết chính xác cách họ đang làm bạn có thể sao chép nguồn của họ trong PHP.

Sự khác biệt lớn giữa cách họ đang thực hiện và cách bạn đang thực hiện, là họ đang sử dụng phân cụm để tìm màu. Thay vì làm tròn màu khi lưu trữ nó, chúng sẽ lưu trữ tất cả các màu nguyên trong một mảng. Sau đó, họ lặp qua mảng này cho đến khi họ tìm thấy một cụm có tỷ lệ điểm cao nhất trong cụm sao cho số lượng màu trong cụm. Điểm trung tâm của điều này là màu phổ biến nhất. Bảng màu sau đó được xác định bởi các tập hợp các cụm cao nhất tiếp theo, với một số logic để ngăn chặn chồng chéo hoàn toàn gần nhau của các cụm.

5

Đây là phương pháp đơn giản của tôi để có được màu sắc chính của một hình ảnh

<?php 

    $image=imagecreatefromjpeg('image.jpg'); 
    $thumb=imagecreatetruecolor(1,1); imagecopyresampled($thumb,$image,0,0,0,0,1,1,imagesx($image),imagesy($image)); 
    $mainColor=strtoupper(dechex(imagecolorat($thumb,0,0))); 
    echo $mainColor; 

?> 
5

Bạn cần phải thu nhỏ hình ảnh và bạn sẽ nhận được các màu chính của hình ảnh. Nếu bạn cần 4 màu trong palet, hãy cân nó xuống khoảng 8x8, 6 màu đến khoảng 12x8 và cứ thế ...

imagecopyresized cho thu nhỏ lại hình ảnh sau đó kiểm tra mỗi pixel và lưu trữ chúng trong mảng imagecolorat($image,px,py)

Hãy thử này ra

<?php 

// EXAMPLE PICTURE 
$url='https://www.nordoff-robbins.org.uk/sites/default/files/google.jpg'; 

//var_dump(getColorPallet($url)); 

echoColors(getColorPallet($url)); 


function echoColors($pallet){ // OUTPUT COLORSBAR 
    foreach ($pallet as $key=>$val) 
     echo '<div style="display:inline-block;width:50px;height:20px;background:#'.$val.'"> </div>'; 
} 

function getColorPallet($imageURL, $palletSize=[16,8]){ // GET PALLET FROM IMAGE PLAY WITH INPUT PALLET SIZE 
    // SIMPLE CHECK INPUT VALUES 
    if(!$imageURL) return false; 

    // IN THIS EXEMPLE WE CREATE PALLET FROM JPG IMAGE 
    $img = imagecreatefromjpeg($imageURL); 

    // SCALE DOWN IMAGE 
    $imgSizes=getimagesize($imageURL); 

    $resizedImg=imagecreatetruecolor($palletSize[0],$palletSize[1]); 

    imagecopyresized($resizedImg, $img , 0, 0 , 0, 0, $palletSize[0], $palletSize[1], $imgSizes[0], $imgSizes[1]); 

    imagedestroy($img); 

    //CHECK IMAGE 
    /*header("Content-type: image/png"); 
    imagepng($resizedImg); 
    die();*/ 

    //GET COLORS IN ARRAY 
    $colors=[]; 

    for($i=0;$i<$palletSize[1];$i++) 
     for($j=0;$j<$palletSize[0];$j++) 
      $colors[]=dechex(imagecolorat($resizedImg,$j,$i)); 

    imagedestroy($resizedImg); 

    //REMOVE DUPLICATES 
    $colors= array_unique($colors); 

    return $colors; 

} 
?> 

Làm việc hoàn hảo cho tôi.

+0

Đây là một ví dụ nhẹ về màu sắc. Có cách nào để giới hạn nó với các màu được sử dụng hàng đầu không. Ví dụ: 8 màu được sử dụng hàng đầu trong một hình ảnh? – JasonDavis

0

Hãy thử điều này: http://www.coolphptools.com/color_extract

Hoạt động với JPEG và PNG.

Và tốt nhất !: không hối hả với nhà soạn nhạc, chỉ cần require_once

require_once 'colorextract/colors.inc.php'; 
$ex=new GetMostCommonColors(); 
$num_results=20; 
$reduce_brightness=1; 
$reduce_gradients=1; 
$delta=24; 
$colors=$ex->Get_Color('image.png', $num_results, $reduce_brightness, $reduce_gradients, $delta); 
print_r($colors); 

cung cấp cho bạn một cái gì đó như thế này:

Array ( [3060a8] => ,55827380952381 [f0a848] => ,19791666666667 [000000] => 0.069642857142857 [483018] => 0.02047619047619 [786018] => 0,0127380952381 [183060] => 0.01797619047619 [4878a8] => ,016011904761905 [181.800] => ,015119047619048 [a87830] => ,014345238095238 [a8c0d8] => ,011904761904762 [6090c0] => ,01172619047619 [d89030] => ,011011904761905 [90a8d8] => ,0071428571428571 [ffffff] => ,0070238095238095 [604.830] => ,006547619047619 [f0f0f0] => ,0063095238095238 [d8d8f0] => ,005297619047619 [c0d8d8] => ,0044047619047619 [f0f0ff] => ,00041666666666667 [181.830] => ,00011904761904762)

Tôi đã thử nó với các hình ảnh khác nhau và có vẻ như nó đáng tin cậy.

Các vấn đề liên quan